diff --git a/CMakeLists.txt b/CMakeLists.txt index 008584e728765..e4cbfb844e0a0 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -464,6 +464,10 @@ option(SWIFT_STDLIB_ASSERTIONS "Enable internal checks for the Swift standard library (useful for debugging the library itself, does not affect checks required for safety)" "${SWIFT_STDLIB_ASSERTIONS_default}") +option(SWIFT_STDLIB_ENABLE_STRICT_AVAILABILITY + "Enable strict availability; this will cause things to break at desk or in CI if the host OS is a lower version than some `@availability` annotations in the runtime code" + FALSE) + option(SWIFT_BUILD_RUNTIME_WITH_HOST_COMPILER "Use the host compiler and not the internal clang to build the swift runtime" FALSE) @@ -1406,8 +1410,9 @@ endif() if(SWIFT_BUILD_STDLIB OR SWIFT_BUILD_SDK_OVERLAY) message(STATUS "Building Swift standard library and overlays for SDKs: ${SWIFT_SDKS}") - message(STATUS " Build type: ${SWIFT_STDLIB_BUILD_TYPE}") - message(STATUS " Assertions: ${SWIFT_STDLIB_ASSERTIONS}") + message(STATUS " Build type: ${SWIFT_STDLIB_BUILD_TYPE}") + message(STATUS " Assertions: ${SWIFT_STDLIB_ASSERTIONS}") + message(STATUS " Strict availability: ${SWIFT_STDLIB_ENABLE_STRICT_AVAILABILITY}") message(STATUS "") message(STATUS "Building Swift runtime with:") diff --git a/Runtimes/Core/CMakeLists.txt b/Runtimes/Core/CMakeLists.txt index 5b090940e6de2..32dcef799247a 100644 --- a/Runtimes/Core/CMakeLists.txt +++ b/Runtimes/Core/CMakeLists.txt @@ -78,7 +78,6 @@ set(SwiftCore_VENDOR_MODULE_DIR "${SwiftCore_CMAKE_MODULES_DIR}/vendor" include(GNUInstallDirs) include(CheckSymbolExists) include(CheckIncludeFileCXX) -include(AvailabilityMacros) include(CompilerSettings) include(DefaultSettings) include(EmitSwiftInterface) @@ -86,6 +85,7 @@ include(PlatformInfo) include(gyb) include(ResourceEmbedding) include(CatalystSupport) +include(AvailabilityMacros) check_symbol_exists("asl_log" "asl.h" SwiftCore_HAS_ASL) check_symbol_exists("dladdr" "dlfcn.h" SwiftCore_HAS_DLADDR) @@ -125,6 +125,7 @@ defaulted_option(SwiftCore_ENABLE_BACKTRACING "Enable backtracing runtime suppor defaulted_set(SwiftCore_BACKTRACER_PATH STRING "Set a fixed path to the Swift backtracer") defaulted_option(SwiftCore_ENABLE_FATALERROR_BACKTRACE "Build stdlib fatalError with backtrace output") defaulted_option(SwiftCore_ENABLE_PRESPECIALIZATION "Enable generic metadata prespecialization") +defaulted_option(SwiftCore_ENABLE_STRICT_AVAILABILITY "Enable strict availability; this will cause things to break at desk or in CI if the host OS is a lower version than some `@availability` annotations in the runtime code") option(SwiftCore_ENABLE_CLOBBER_FREED_OBJECTS "" OFF) option(SwiftCore_ENABLE_RUNTIME_LEAK_CHECKER "" OFF) diff --git a/Runtimes/Core/cmake/caches/Vendors/Apple/apple-common.cmake b/Runtimes/Core/cmake/caches/Vendors/Apple/apple-common.cmake index 4a921adfa6b0c..abf1ecbb46827 100644 --- a/Runtimes/Core/cmake/caches/Vendors/Apple/apple-common.cmake +++ b/Runtimes/Core/cmake/caches/Vendors/Apple/apple-common.cmake @@ -12,6 +12,8 @@ set(SwiftCore_ENABLE_VECTOR_TYPES ON CACHE BOOL "") set(SwiftCore_ENABLE_RUNTIME_FUNCTION_COUNTERS ON CACHE BOOL "") set(SwiftCore_ENABLE_BACKDEPLOYMENT_SUPPORT ON CACHE BOOL "") set(SwiftCore_ENABLE_FILESYSTEM_SUPPORT ON CACHE BOOL "") +set(SwiftCore_ENABLE_STRICT_AVAILABILITY ON CACHE BOOL "") + set(SwiftCore_OPTIMIZATION_REMARKS "bitstream" CACHE STRING "") set(SwiftCore_INSTALL_NESTED_SUBDIR OFF CACHE BOOL "") diff --git a/Runtimes/Core/cmake/modules/AvailabilityMacros.cmake b/Runtimes/Core/cmake/modules/AvailabilityMacros.cmake index 1e82bac48a399..5f3f21985ef9e 100644 --- a/Runtimes/Core/cmake/modules/AvailabilityMacros.cmake +++ b/Runtimes/Core/cmake/modules/AvailabilityMacros.cmake @@ -4,5 +4,39 @@ configure_file("${SwiftCore_SWIFTC_SOURCE_DIR}/utils/availability-macros.def" file(STRINGS "${CMAKE_CURRENT_BINARY_DIR}/availability-macros.def" availability_defs) list(FILTER availability_defs EXCLUDE REGEX "^\\s*(#.*)?$") foreach(def ${availability_defs}) - add_compile_options("$<$:SHELL:-Xfrontend -define-availability -Xfrontend \"${def}\">") + list(APPEND availability_definitions "-Xfrontend -define-availability -Xfrontend \"${def}\"") + + if("${def}" MATCHES "SwiftStdlib .*") + # For each SwiftStdlib x.y, also define StdlibDeploymentTarget x.y, which, + # will expand to the current `-target` platform if the macro defines a + # newer platform as its availability. + # + # There is a setting, SwiftCore_ENABLE_STRICT_AVAILABILITY, which if set + # ON will cause us to use the "proper" availability instead. + string(REPLACE "SwiftStdlib" "StdlibDeploymentTarget" current "${def}") + if(NOT SwiftCore_ENABLE_STRICT_AVAILABILITY AND SwiftCore_SWIFT_AVAILABILITY_PLATFORM) + if("${SwiftCore_SWIFT_AVAILABILITY_PLATFORM}" STREQUAL "macOS" AND "${SwiftCore_VARIANT_AVAILABILITY_PLATFORM}" STREQUAL "iOS") + string(REGEX MATCH "iOS ([0-9]+(\.[0-9]+)+)" ios_platform_version "${def}") + string(REGEX MATCH "[0-9]+(\.[0-9]+)+" ios_version "${ios_platform_version}") + string(REGEX MATCH "macOS ([0-9]+(\.[0-9]+)+)" macos_platform_version "${def}") + string(REGEX MATCH "[0-9]+(\.[0-9]+)+" macos_version "${macos_platform_version}") + if((NOT macos_version STREQUAL "9999" OR NOT ios_version STREQUAL "9999") AND (macos_version VERSION_GREATER CMAKE_OSX_DEPLOYMENT_TARGET OR ios_version VERSION_GREATER SwiftCore_VARIANT_DEPLOYMENT_VERSION)) + string(REGEX REPLACE ":.*" ": macOS ${CMAKE_OSX_DEPLOYMENT_VERSION}, iOS ${SwiftCore_VARIANT_DEPLOYMENT_VERSION}" current "${current}") + endif() + else() + string(REGEX MATCH "${SwiftCore_SWIFT_AVAILABILITY_PLATFORM} ([0-9]+(\.[0-9]+)+)" platform_version "${def}") + string(REGEX MATCH "[0-9]+(\.[0-9]+)+" version "${platform_version}") + if(NOT version STREQUAL "9999" AND version VERSION_GREATER CMAKE_OSX_DEPLOYMENT_TARGET) + string(REGEX REPLACE ":.*" ":${SwiftCore_SWIFT_AVAILABILITY_PLATFORM} ${CMAKE_OSX_DEPLOYMENT_TARGET}" current "${current}") + endif() + endif() + endif() + list(APPEND availability_definitions "-Xfrontend -define-availability -Xfrontend \"${current}\"") + endif() endforeach() + +list(JOIN availability_definitions "\n" availability_definitions) +file(GENERATE + OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/availability-macros.rsp" + CONTENT "${availability_definitions}") +add_compile_options("$<$:SHELL:${CMAKE_Swift_RESPONSE_FILE_FLAG}${CMAKE_CURRENT_BINARY_DIR}/availability-macros.rsp>") diff --git a/Runtimes/Core/cmake/modules/CatalystSupport.cmake b/Runtimes/Core/cmake/modules/CatalystSupport.cmake index 7f761007414ea..1ac17eb9b554e 100644 --- a/Runtimes/Core/cmake/modules/CatalystSupport.cmake +++ b/Runtimes/Core/cmake/modules/CatalystSupport.cmake @@ -34,5 +34,12 @@ if(SwiftCore_COMPILER_VARIANT_TARGET) set(SwiftCore_VARIANT_MODULE_TRIPLE "${module_triple}" CACHE STRING "Triple used for installed swift{module,interface} files for the target variant") mark_as_advanced(SwiftCore_VARIANT_MODULE_TRIPLE) message(CONFIGURE_LOG "Swift target variant module triple: ${module_triple}") + + string(JSON triple GET "${target_info_json}" "target" "triple") + if(triple MATCHES "apple-([a-zA-Z]+)([0-9]+[.0-9]*)-macabi") + set(SwiftCore_VARIANT_DEPLOYMENT_VERSION "${CMAKE_MATCH_2}") + mark_as_advanced(SwiftCore_VARIANT_DEPLOYMENT_VERSION) + message(CONFIGURE_LOG "Swift target variant deployment version: ${SwiftCore_VARIANT_DEPLOYMENT_VERSION}") + endif() endif() endif() diff --git a/Runtimes/Core/cmake/modules/DefaultSettings.cmake b/Runtimes/Core/cmake/modules/DefaultSettings.cmake index e6fc1f5820ef0..3ff9b9da16e12 100644 --- a/Runtimes/Core/cmake/modules/DefaultSettings.cmake +++ b/Runtimes/Core/cmake/modules/DefaultSettings.cmake @@ -11,6 +11,8 @@ set(SwiftCore_ENABLE_COMMANDLINE_SUPPORT_default OFF) # TODO: enable this by def set(SwiftCore_ENABLE_STDIN_default ON) set(SwiftCore_ENABLE_TYPE_PRINTING_default ON) +set(SwiftCore_ENABLE_STRICT_AVAILABILITY_default OFF) + set(SwiftCore_BACKTRACER_PATH_default "") # Provide a boolean option that a user can optionally enable. @@ -20,7 +22,7 @@ macro(defaulted_option variable helptext) if(NOT DEFINED ${variable}_default) set(${variable}_default OFF) endif() - option(${variable} ${helptext} ${${variable}_default}) + option(${variable} "${helptext}" ${${variable}_default}) endmacro() # Create a defaulted cache entry diff --git a/Runtimes/Core/cmake/modules/PlatformInfo.cmake b/Runtimes/Core/cmake/modules/PlatformInfo.cmake index 999d6b0595f1b..90a0030eecea5 100644 --- a/Runtimes/Core/cmake/modules/PlatformInfo.cmake +++ b/Runtimes/Core/cmake/modules/PlatformInfo.cmake @@ -36,3 +36,47 @@ if(NOT SwiftCore_ARCH_SUBDIR) message(CONFIGURE_LOG "Swift Arch: ${arch}") endif() + +# Note: *moduleTriple* doesn't have an "x" on the end of "macos"; just to be +# safe, we support both cases here. +set(availability_platform_macos "macOS") +set(availaiblity_platform_macosx "macOS") +set(availability_platform_ios "iOS") +set(availability_platform_watchos "watchOS") +set(availability_platform_tvos "tvOS") +set(availability_platform_xros "visionOS") +set(availability_platform_bridgeos "bridgeOS") + +if(NOT SwiftCore_SWIFT_AVAILABILITY_PLATFORM) + if(SwiftCore_MODULE_TRIPLE MATCHES ".*-([^-]+)-simulator$") + set(platform "${CMAKE_MATCH_1}") + elseif(SwiftCore_MODULE_TRIPLE MATCHES ".*-([^-]+)-msvc$") + set(platform "${CMAKE_MATCH_1}") + elseif(SwiftCore_MODULE_TRIPLE MATCHES ".*-([^-]+)$") + set(platform "${CMAKE_MATCH_1}") + else() + message(WARNING "Unable to extract platform name from triple ${SwiftCore_MODULE_TRIPLE}") + endif() + + if(availability_platform_${platform}) + set(SwiftCore_SWIFT_AVAILABILITY_PLATFORM "${availability_platform_${platform}}") + else() + set(SwiftCore_SWIFT_AVAILABILITY_PLATFORM "unknown") + message(WARNING "Unknown platform ${platform} for availability") + endif() +endif() + +set(SwiftCore_VARIANT_AVAILABILITY_PLATFORM "none") +if(SwiftCore_VARIANT_MODULE_TRIPLE) + if(SwiftCore_VARIANT_MODULE_TRIPLE MATCHES ".*-([^-]+)$") + set(platform "${CMAKE_MATCH_1}") + else() + message(FATAL_ERROR "Unable to extract platform name from triple ${SwiftCore_VARIANT_MODULE_TRIPLE}") + endif() + + if(availability_platform_${platform}) + set(SwiftCore_VARIANT_AVAILABILITY_PLATFORM "${availability_platform_${platform}}") + else() + message(WARNING "Unknown platform ${platform} for variant availability") + endif() +endif() diff --git a/cmake/modules/DarwinSDKs.cmake b/cmake/modules/DarwinSDKs.cmake index 20d555b74751c..113e0eca9bf95 100644 --- a/cmake/modules/DarwinSDKs.cmake +++ b/cmake/modules/DarwinSDKs.cmake @@ -12,7 +12,7 @@ is_sdk_requested(OSX swift_build_osx) if(swift_build_osx) configure_sdk_darwin( OSX "OS X" "${SWIFT_DARWIN_DEPLOYMENT_VERSION_OSX}" - macosx macosx macos "${SUPPORTED_OSX_ARCHS}") + macosx macosx macos macOS "${SUPPORTED_OSX_ARCHS}") configure_target_variant(OSX-DA "OS X Debug+Asserts" OSX DA "Debug+Asserts") configure_target_variant(OSX-RA "OS X Release+Asserts" OSX RA "Release+Asserts") configure_target_variant(OSX-R "OS X Release" OSX R "Release") @@ -22,16 +22,21 @@ is_sdk_requested(FREESTANDING swift_build_freestanding) if(swift_build_freestanding AND (SWIFT_FREESTANDING_FLAVOR STREQUAL "apple")) set(SWIFT_FREESTANDING_SDK "" CACHE STRING "Which SDK to use when building the FREESTANDING stdlib") + set(SWIFT_FREESTANDING_DEPLOYMENT_VERSION "" CACHE STRING + "The deployment version to use when building the FREESTANDING stdlib") set(SWIFT_FREESTANDING_TRIPLE_NAME "" CACHE STRING "Which triple name (e.g. 'none-macho') to use when building the FREESTANDING stdlib") set(SWIFT_FREESTANDING_MODULE_NAME "" CACHE STRING "Which .swiftmodule name (e.g. 'freestanding') to use when building the FREESTANDING stdlib") + set(SWIFT_FREESTANDING_AVAILABILITY_NAME "" CACHE STRING + "Which @availability name (e.g. 'macOS') to use when building the FREESTANDING stdlib") set(SWIFT_FREESTANDING_ARCHS "" CACHE STRING "Which architectures to build when building the FREESTANDING stdlib") configure_sdk_darwin( - FREESTANDING "FREESTANDING" "" + FREESTANDING "FREESTANDING" "${SWIFT_FREESTANDING_DEPLOYMENT_VERSION}" "${SWIFT_FREESTANDING_SDK}" - "${SWIFT_FREESTANDING_TRIPLE_NAME}" "${SWIFT_FREESTANDING_MODULE_NAME}" "${SWIFT_FREESTANDING_ARCHS}") + "${SWIFT_FREESTANDING_TRIPLE_NAME}" "${SWIFT_FREESTANDING_MODULE_NAME}" + "${SWIFT_FREESTANDING_AVAILABILITY_NAME}" "${SWIFT_FREESTANDING_ARCHS}") set(SWIFT_SDK_FREESTANDING_LIB_SUBDIR "freestanding") configure_target_variant(FREESTANDING-DA "FREESTANDING Debug+Asserts" FREESTANDING DA "Debug+Asserts") configure_target_variant(FREESTANDING-RA "FREESTANDING Release+Asserts" FREESTANDING RA "Release+Asserts") @@ -53,7 +58,7 @@ is_sdk_requested(IOS swift_build_ios) if(swift_build_ios) configure_sdk_darwin( IOS "iOS" "${SWIFT_DARWIN_DEPLOYMENT_VERSION_IOS}" - iphoneos ios ios "${SUPPORTED_IOS_ARCHS}") + iphoneos ios ios iOS "${SUPPORTED_IOS_ARCHS}") configure_target_variant(IOS-DA "iOS Debug+Asserts" IOS DA "Debug+Asserts") configure_target_variant(IOS-RA "iOS Release+Asserts" IOS RA "Release+Asserts") configure_target_variant(IOS-R "iOS Release" IOS R "Release") @@ -63,7 +68,7 @@ is_sdk_requested(IOS_SIMULATOR swift_build_ios_simulator) if(swift_build_ios_simulator) configure_sdk_darwin( IOS_SIMULATOR "iOS Simulator" "${SWIFT_DARWIN_DEPLOYMENT_VERSION_IOS}" - iphonesimulator ios ios-simulator + iphonesimulator ios ios-simulator iOS "${SUPPORTED_IOS_SIMULATOR_ARCHS}") configure_target_variant( IOS_SIMULATOR-DA "iOS Debug+Asserts" IOS_SIMULATOR DA "Debug+Asserts") @@ -77,7 +82,7 @@ is_sdk_requested(TVOS swift_build_tvos) if(swift_build_tvos) configure_sdk_darwin( TVOS "tvOS" "${SWIFT_DARWIN_DEPLOYMENT_VERSION_TVOS}" - appletvos tvos tvos "${SUPPORTED_TVOS_ARCHS}") + appletvos tvos tvos tvOS "${SUPPORTED_TVOS_ARCHS}") configure_target_variant(TVOS-DA "tvOS Debug+Asserts" TVOS DA "Debug+Asserts") configure_target_variant(TVOS-RA "tvOS Release+Asserts" TVOS RA "Release+Asserts") configure_target_variant(TVOS-R "tvOS Release" TVOS R "Release") @@ -87,7 +92,7 @@ is_sdk_requested(TVOS_SIMULATOR swift_build_tvos_simulator) if(swift_build_tvos_simulator) configure_sdk_darwin( TVOS_SIMULATOR "tvOS Simulator" "${SWIFT_DARWIN_DEPLOYMENT_VERSION_TVOS}" - appletvsimulator tvos tvos-simulator + appletvsimulator tvos tvos-simulator tvOS "${SUPPORTED_TVOS_SIMULATOR_ARCHS}") configure_target_variant( TVOS_SIMULATOR-DA "tvOS Debug+Asserts" TVOS_SIMULATOR DA "Debug+Asserts") @@ -101,7 +106,7 @@ is_sdk_requested(WATCHOS swift_build_watchos) if(swift_build_watchos) configure_sdk_darwin( WATCHOS "watchOS" "${SWIFT_DARWIN_DEPLOYMENT_VERSION_WATCHOS}" - watchos watchos watchos "${SUPPORTED_WATCHOS_ARCHS}") + watchos watchos watchos watchOS "${SUPPORTED_WATCHOS_ARCHS}") configure_target_variant(WATCHOS-DA "watchOS Debug+Asserts" WATCHOS DA "Debug+Asserts") configure_target_variant(WATCHOS-RA "watchOS Release+Asserts" WATCHOS RA "Release+Asserts") configure_target_variant(WATCHOS-R "watchOS Release" WATCHOS R "Release") @@ -111,7 +116,7 @@ is_sdk_requested(WATCHOS_SIMULATOR swift_build_watchos_simulator) if(swift_build_watchos_simulator) configure_sdk_darwin( WATCHOS_SIMULATOR "watchOS Simulator" "${SWIFT_DARWIN_DEPLOYMENT_VERSION_WATCHOS}" - watchsimulator watchos watchos-simulator + watchsimulator watchos watchos-simulator watchOS "${SUPPORTED_WATCHOS_SIMULATOR_ARCHS}") configure_target_variant(WATCHOS_SIMULATOR-DA "watchOS Debug+Asserts" WATCHOS_SIMULATOR DA "Debug+Asserts") configure_target_variant(WATCHOS_SIMULATOR-RA "watchOS Release+Asserts" WATCHOS_SIMULATOR RA "Release+Asserts") @@ -122,7 +127,7 @@ is_sdk_requested(XROS swift_build_xros) if(swift_build_xros) configure_sdk_darwin( XROS "xrOS" "${SWIFT_DARWIN_DEPLOYMENT_VERSION_XROS}" - xros xros xros "${SUPPORTED_XROS_ARCHS}") + xros xros xros visionOS "${SUPPORTED_XROS_ARCHS}") configure_target_variant(XROS-DA "xrOS Debug+Asserts" XROS DA "Debug+Asserts") configure_target_variant(XROS-RA "xrOS Release+Asserts" XROS RA "Release+Asserts") configure_target_variant(XROS-R "xrOS Release" XROS R "Release") @@ -132,7 +137,7 @@ is_sdk_requested(XROS_SIMULATOR swift_build_xros_simulator) if(swift_build_xros_simulator) configure_sdk_darwin( XROS_SIMULATOR "xrOS Simulator" "${SWIFT_DARWIN_DEPLOYMENT_VERSION_XROS}" - xrsimulator xros xros-simulator + xrsimulator xros xros-simulator visionOS "${SUPPORTED_XROS_SIMULATOR_ARCHS}") configure_target_variant( diff --git a/cmake/modules/SwiftConfigureSDK.cmake b/cmake/modules/SwiftConfigureSDK.cmake index 11fbebe9659c1..c8bff5d57e0bb 100644 --- a/cmake/modules/SwiftConfigureSDK.cmake +++ b/cmake/modules/SwiftConfigureSDK.cmake @@ -136,6 +136,7 @@ endfunction() # deployment_version # Deployment version # xcrun_name # SDK name to use with xcrun # triple_name # The name used in Swift's -triple +# availability_name # The name used in Swift's @availability # architectures # A list of architectures this SDK supports # ) # @@ -165,9 +166,11 @@ endfunction() # SWIFT_SDK_${prefix}_ARCH_${ARCH}_TRIPLE Triple name # SWIFT_SDK_${prefix}_ARCH_${ARCH}_MODULE Module triple name for this SDK # SWIFT_SDK_${prefix}_USE_BUILD_ID Whether to pass --build-id to the linker +# SWIFT_SDK_${prefix}_AVAILABILITY_NAME Name to use in @availability +# macro(configure_sdk_darwin prefix name deployment_version xcrun_name - triple_name module_name architectures) + triple_name module_name availability_name architectures) # Note: this has to be implemented as a macro because it sets global # variables. @@ -201,6 +204,7 @@ macro(configure_sdk_darwin set(SWIFT_SDK_${prefix}_DEPLOYMENT_VERSION "${deployment_version}") set(SWIFT_SDK_${prefix}_LIB_SUBDIR "${xcrun_name}") set(SWIFT_SDK_${prefix}_TRIPLE_NAME "${triple_name}") + set(SWIFT_SDK_${prefix}_AVAILABILITY_NAME "${availability_name}") set(SWIFT_SDK_${prefix}_OBJECT_FORMAT "MACHO") set(SWIFT_SDK_${prefix}_USE_ISYSROOT TRUE) set(SWIFT_SDK_${prefix}_SHARED_LIBRARY_PREFIX "lib") diff --git a/stdlib/cmake/modules/AddSwiftStdlib.cmake b/stdlib/cmake/modules/AddSwiftStdlib.cmake index ce113989ad75d..0b18957eadb31 100644 --- a/stdlib/cmake/modules/AddSwiftStdlib.cmake +++ b/stdlib/cmake/modules/AddSwiftStdlib.cmake @@ -1003,6 +1003,41 @@ function(add_swift_target_library_single target name) # Define availability macros. foreach(def ${SWIFT_STDLIB_AVAILABILITY_DEFINITIONS}) list(APPEND SWIFTLIB_SINGLE_SWIFT_COMPILE_FLAGS "-Xfrontend" "-define-availability" "-Xfrontend" "${def}") + + if("${def}" MATCHES "SwiftStdlib .*") + # For each SwiftStdlib x.y, also define StdlibDeploymentTarget x.y, which, + # will expand to the current `-target` platform if the macro defines a + # newer platform as its availability. + # + # There is a setting, SWIFT_STDLIB_ENABLE_STRICT_AVAILABILITY, which if set + # ON will cause us to use the "proper" availability instead. + string(REPLACE "SwiftStdlib" "StdlibDeploymentTarget" current "${def}") + if(NOT SWIFT_STDLIB_ENABLE_STRICT_AVAILABILITY AND SWIFT_SDK_${SWIFTLIB_SINGLE_SDK}_AVAILABILITY_NAME) + if(SWIFTLIB_SINGLE_SDK STREQUAL "OSX" AND SWIFTLIB_SINGLE_MACCATALYST_BUILD_FLAVOR STREQUAL "ios-like") + string(REGEX MATCH "iOS ([0-9]+(\.[0-9]+)+)" platform_version "${def}") + string(REGEX MATCH "[0-9]+(\.[0-9]+)+" version "${platform_version}") + if(NOT version STREQUAL "9999" AND version VERSION_GREATER "${SWIFT_DARWIN_DEPLOYMENT_VERSION_MACCATALYST}") + string(REGEX REPLACE ":.*" ":iOS ${SWIFT_DARWIN_DEPLOYMENT_VERSION_MACCATALYST}" current "${current}") + endif() + elseif(SWIFTLIB_SINGLE_SDK STREQUAL "OSX" AND SWIFTLIB_SINGLE_MACCATALYST_BUILD_FLAVOR STREQUAL "zippered") + string(REGEX MATCH "iOS ([0-9]+(\.[0-9]+)+)" ios_platform_version "${def}") + string(REGEX MATCH "[0-9]+(\.[0-9]+)+" ios_version "${ios_platform_version}") + string(REGEX MATCH "macOS ([0-9]+(\.[0-9]+)+)" macos_platform_version "${def}") + string(REGEX MATCH "[0-9]+(\.[0-9]+)+" macos_version "${macos_platform_version}") + if((NOT macos_version STREQUAL "9999" OR NOT ios_version STREQUAL "9999") AND (macos_version VERSION_GREATER "${SWIFT_SDK_OSX_DEPLOYMENT_VERSION}" OR ios_version VERSION_GREATER "${SWIFT_DARWIN_DEPLOYMENT_VERSION_MACCATALYST}")) + string(REGEX REPLACE ":.*" ": macOS ${SWIFT_SDK_OSX_DEPLOYMENT_VERSION}, iOS ${SWIFT_DARWIN_DEPLOYMENT_VERSION_MACCATALYST}" current "${current}") + endif() + else() + string(REGEX MATCH "${SWIFT_SDK_${SWIFTLIB_SINGLE_SDK}_AVAILABILITY_NAME} ([0-9]+(\.[0-9]+)+)" platform_version "${def}") + string(REGEX MATCH "[0-9]+(\.[0-9]+)+" version "${platform_version}") + if(NOT version STREQUAL "9999" AND version VERSION_GREATER "${SWIFT_SDK_${SWIFTLIB_SINGLE_SDK}_DEPLOYMENT_VERSION}") + string(REGEX REPLACE ":.*" ":${SWIFT_SDK_${SWIFTLIB_SINGLE_SDK}_AVAILABILITY_NAME} ${SWIFT_SDK_${SWIFTLIB_SINGLE_SDK}_DEPLOYMENT_VERSION}" current "${current}") + endif() + endif() + endif() + + list(APPEND SWIFTLIB_SINGLE_SWIFT_COMPILE_FLAGS "-Xfrontend" "-define-availability" "-Xfrontend" "${current}") + endif() endforeach() # Enable -target-min-inlining-version diff --git a/stdlib/public/Concurrency/CFExecutor.swift b/stdlib/public/Concurrency/CFExecutor.swift index 451e0860e7975..7a6a08918e3b5 100644 --- a/stdlib/public/Concurrency/CFExecutor.swift +++ b/stdlib/public/Concurrency/CFExecutor.swift @@ -43,7 +43,7 @@ enum CoreFoundation { // .. Main Executor ............................................................ -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public final class CFMainExecutor: DispatchMainExecutor, @unchecked Sendable { override public func run() throws { @@ -58,7 +58,7 @@ public final class CFMainExecutor: DispatchMainExecutor, @unchecked Sendable { // .. Task Executor ............................................................ -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public final class CFTaskExecutor: DispatchGlobalTaskExecutor, @unchecked Sendable { diff --git a/stdlib/public/Concurrency/CMakeLists.txt b/stdlib/public/Concurrency/CMakeLists.txt index d88f23d689e35..bdc646da3d97f 100644 --- a/stdlib/public/Concurrency/CMakeLists.txt +++ b/stdlib/public/Concurrency/CMakeLists.txt @@ -213,6 +213,13 @@ set(SWIFT_CONCURRENCY_GYB_SOURCES Task+immediate.swift.gyb ) +# Build with a minimum deployment target of 10.15 +if(SWIFT_DARWIN_DEPLOYMENT_VERSION_OSX VERSION_LESS "10.15") + set(osx_deployment_target "10.15") +else() + set(osx_deployment_target "${SWIFT_DARWIN_DEPLOYMENT_VERSION_OSX}") +endif() + add_swift_target_library(swift_Concurrency ${SWIFT_STDLIB_LIBRARY_BUILD_TYPES} IS_STDLIB ${SWIFT_RUNTIME_CONCURRENCY_C_SOURCES} ${SWIFT_RUNTIME_CONCURRENCY_EXECUTOR_SOURCES} @@ -237,6 +244,8 @@ add_swift_target_library(swift_Concurrency ${SWIFT_STDLIB_LIBRARY_BUILD_TYPES} I ${swift_concurrency_incorporate_object_libraries_so} LINK_LIBRARIES ${swift_concurrency_link_libraries} + DEPLOYMENT_VERSION_OSX ${osx_deployment_target} + C_COMPILE_FLAGS -Dswift_Concurrency_EXPORTS ${SWIFT_RUNTIME_CONCURRENCY_C_FLAGS} -I${SWIFT_SOURCE_DIR}/stdlib/include diff --git a/stdlib/public/Concurrency/Clock.swift b/stdlib/public/Concurrency/Clock.swift index 8c6864ca3447c..39e08c9bd9a8b 100644 --- a/stdlib/public/Concurrency/Clock.swift +++ b/stdlib/public/Concurrency/Clock.swift @@ -30,7 +30,7 @@ import Swift /// /// For more information about specific clocks see `ContinuousClock` and /// `SuspendingClock`. -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) public protocol Clock: Sendable { associatedtype Duration associatedtype Instant: InstantProtocol where Instant.Duration == Duration @@ -43,7 +43,7 @@ public protocol Clock: Sendable { #endif /// The traits associated with this clock instance. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) var traits: ClockTraits { get } /// Convert a Clock-specific Duration to a Swift Duration @@ -59,7 +59,7 @@ public protocol Clock: Sendable { /// /// Returns: A `Swift.Duration` representing the equivalent duration, or /// `nil` if this function is not supported. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) func convert(from duration: Duration) -> Swift.Duration? /// Convert a Swift Duration to a Clock-specific Duration @@ -70,7 +70,7 @@ public protocol Clock: Sendable { /// /// Returns: A `Duration` representing the equivalent duration, or /// `nil` if this function is not supported. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) func convert(from duration: Swift.Duration) -> Duration? /// Convert an `Instant` from some other clock's `Instant` @@ -82,12 +82,12 @@ public protocol Clock: Sendable { /// /// Returns: An `Instant` representing the equivalent instant, or /// `nil` if this function is not supported. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) func convert(instant: OtherClock.Instant, from clock: OtherClock) -> Instant? } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Clock { /// Measure the elapsed time to execute a closure. /// @@ -95,7 +95,7 @@ extension Clock { /// let elapsed = clock.measure { /// someWork() /// } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public func measure(_ work: () throws -> Void) rethrows -> Instant.Duration { let start = now try work() @@ -109,7 +109,7 @@ extension Clock { /// let elapsed = await clock.measure { /// await someWork() /// } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) @_alwaysEmitIntoClient public func measure( isolation: isolated (any Actor)? = #isolation, @@ -127,7 +127,7 @@ extension Clock { // // This function also doubles as an ABI-compatibility shim predating the // introduction of #isolation. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) @_silgen_name("$ss5ClockPsE7measurey8DurationQzyyYaKXEYaKF") @_unsafeInheritExecutor // for ABI compatibility public func _unsafeInheritExecutor_measure( @@ -140,7 +140,7 @@ extension Clock { } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension Clock { // For compatibility, return `nil` if this is not implemented public func convert(from duration: Duration) -> Swift.Duration? { @@ -171,7 +171,7 @@ extension Clock { } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension Clock where Duration == Swift.Duration { public func convert(from duration: Duration) -> Duration? { return duration @@ -179,13 +179,13 @@ extension Clock where Duration == Swift.Duration { } #if !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Clock { /// Suspends for the given duration. /// /// Prefer to use the `sleep(until:tolerance:)` method on `Clock` if you have /// access to an absolute instant. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) @_alwaysEmitIntoClient public func sleep( for duration: Instant.Duration, @@ -207,7 +207,7 @@ extension Clock { /// clocks best matches the clock that the user is trying to specify a /// time or delay in. Executors are expected to do this on a best effort /// basis. -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public struct ClockTraits: OptionSet { public let rawValue: UInt32 @@ -225,10 +225,10 @@ public struct ClockTraits: OptionSet { public static let wallTime = ClockTraits(rawValue: 1 << 2) } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension Clock { /// The traits associated with this clock instance. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public var traits: ClockTraits { return [] } @@ -239,21 +239,21 @@ enum _ClockID: Int32 { case suspending = 2 } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_silgen_name("swift_get_time") internal func _getTime( seconds: UnsafeMutablePointer, nanoseconds: UnsafeMutablePointer, clock: CInt) -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_silgen_name("swift_get_clock_res") internal func _getClockRes( seconds: UnsafeMutablePointer, nanoseconds: UnsafeMutablePointer, clock: CInt) -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_sleep") internal func _sleep( seconds: Int64, diff --git a/stdlib/public/Concurrency/ContinuousClock.swift b/stdlib/public/Concurrency/ContinuousClock.swift index 979a3580d17ea..495fc120d3b99 100644 --- a/stdlib/public/Concurrency/ContinuousClock.swift +++ b/stdlib/public/Concurrency/ContinuousClock.swift @@ -20,7 +20,7 @@ import Swift /// only comparable locally during the execution of a program. /// /// This clock is suitable for high resolution measurements of execution. -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded public struct ContinuousClock: Sendable { /// A continuous point in time used for `ContinuousClock`. @@ -36,12 +36,12 @@ public struct ContinuousClock: Sendable { } #if !$Embedded -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension ContinuousClock.Instant: Codable { } #endif -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Duration { internal init(_seconds s: Int64, nanoseconds n: Int64) { let (secHi, secLo) = s.multipliedFullWidth(by: 1_000_000_000_000_000_000) @@ -56,7 +56,7 @@ extension Duration { } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded extension Clock where Self == ContinuousClock { /// A clock that measures time that always increments but does not stop @@ -64,11 +64,11 @@ extension Clock where Self == ContinuousClock { /// /// try await Task.sleep(until: .now + .seconds(3), clock: .continuous) /// - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static var continuous: ContinuousClock { return ContinuousClock() } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded extension ContinuousClock: Clock { /// The current continuous instant. @@ -101,7 +101,7 @@ extension ContinuousClock: Clock { } /// The continuous clock is continuous and monotonic - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public var traits: ClockTraits { return [.continuous, .monotonic] } @@ -119,17 +119,16 @@ extension ContinuousClock: Clock { public func sleep( until deadline: Instant, tolerance: Swift.Duration? = nil ) async throws { - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { try await Task._sleep(until: deadline, tolerance: tolerance, clock: self) } else { - // Should never see this - Builtin.unreachable() + fatalError("we should never get here; if we have, availability is broken") } } #else - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) @available(*, unavailable, message: "Unavailable in task-to-thread concurrency model") public func sleep( until deadline: Instant, tolerance: Swift.Duration? = nil @@ -139,7 +138,7 @@ extension ContinuousClock: Clock { #endif } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded extension ContinuousClock.Instant: InstantProtocol { public static var now: ContinuousClock.Instant { ContinuousClock.now } diff --git a/stdlib/public/Concurrency/CooperativeExecutor.swift b/stdlib/public/Concurrency/CooperativeExecutor.swift index 794f9fc542a2a..3e92e85dde67f 100644 --- a/stdlib/public/Concurrency/CooperativeExecutor.swift +++ b/stdlib/public/Concurrency/CooperativeExecutor.swift @@ -17,7 +17,7 @@ import Swift // Store the Timestamp in the executor private data, if it will fit; otherwise, // use the allocator to allocate space for it and stash a pointer in the private // data area. -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension ExecutorJob { fileprivate var cooperativeExecutorTimestampIsIndirect: Bool { return MemoryLayout<(Int, Int)>.size @@ -99,7 +99,7 @@ extension ExecutorJob { /// A co-operative executor that can be used as the main executor or as a /// task executor. -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) class CooperativeExecutor: Executor, @unchecked Sendable { var runQueue: PriorityQueue var waitQueue: PriorityQueue @@ -179,7 +179,7 @@ class CooperativeExecutor: Executor, @unchecked Sendable { public var asSchedulable: any SchedulableExecutor { self } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension CooperativeExecutor: SchedulableExecutor { var currentTime: Timestamp { var now: Timestamp = .zero @@ -202,7 +202,7 @@ extension CooperativeExecutor: SchedulableExecutor { } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension CooperativeExecutor: RunLoopExecutor { public func run() throws { try runUntil { false } @@ -249,13 +249,13 @@ extension CooperativeExecutor: RunLoopExecutor { } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension CooperativeExecutor: SerialExecutor {} -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension CooperativeExecutor: TaskExecutor {} -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension CooperativeExecutor: MainExecutor {} #endif // !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY diff --git a/stdlib/public/Concurrency/DispatchExecutor.swift b/stdlib/public/Concurrency/DispatchExecutor.swift index 11a372b14d1f9..8ba61976f1d4a 100644 --- a/stdlib/public/Concurrency/DispatchExecutor.swift +++ b/stdlib/public/Concurrency/DispatchExecutor.swift @@ -23,7 +23,7 @@ import Swift // .. Main Executor ............................................................ -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public class DispatchMainExecutor: RunLoopExecutor, @unchecked Sendable { var threaded = false @@ -43,7 +43,7 @@ public class DispatchMainExecutor: RunLoopExecutor, @unchecked Sendable { } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension DispatchMainExecutor: SerialExecutor { public func enqueue(_ job: consuming ExecutorJob) { @@ -57,7 +57,7 @@ extension DispatchMainExecutor: SerialExecutor { } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension DispatchMainExecutor: SchedulableExecutor { public var asSchedulable: SchedulableExecutor? { return self @@ -85,12 +85,12 @@ extension DispatchMainExecutor: SchedulableExecutor { } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension DispatchMainExecutor: MainExecutor {} // .. Task Executor ............................................................ -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public class DispatchGlobalTaskExecutor: TaskExecutor, SchedulableExecutor, @unchecked Sendable { public init() {} @@ -130,7 +130,7 @@ public class DispatchGlobalTaskExecutor: TaskExecutor, SchedulableExecutor, /// /// It is used to help convert instants and durations from arbitrary `Clock`s /// to Dispatch's time base. -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) protocol DispatchExecutorProtocol: Executor { /// Convert an `Instant` from the specified clock to a tuple identifying @@ -158,7 +158,7 @@ enum DispatchClockID: CInt { case suspending = 2 } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension DispatchExecutorProtocol { func clamp(_ components: (seconds: Int64, attoseconds: Int64)) @@ -201,11 +201,11 @@ extension DispatchExecutorProtocol { } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension DispatchGlobalTaskExecutor: DispatchExecutorProtocol { } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension DispatchMainExecutor: DispatchExecutorProtocol { } diff --git a/stdlib/public/Concurrency/Executor.swift b/stdlib/public/Concurrency/Executor.swift index 2101d6a821fa1..37897059602b2 100644 --- a/stdlib/public/Concurrency/Executor.swift +++ b/stdlib/public/Concurrency/Executor.swift @@ -26,24 +26,24 @@ public protocol Executor: AnyObject, Sendable { // Cannot introduce these methods in SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY // since it lacks move-only type support. #if !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) @available(*, deprecated, message: "Implement 'enqueue(_: consuming ExecutorJob)' instead") func enqueue(_ job: consuming Job) #endif // !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY #if !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) func enqueue(_ job: consuming ExecutorJob) #endif // !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY #if !$Embedded /// `true` if this is the main executor. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) var isMainExecutor: Bool { get } #endif } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public protocol SchedulableExecutor: Executor { #if !$Embedded && !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY @@ -63,7 +63,7 @@ public protocol SchedulableExecutor: Executor { /// - tolerance: The maximum additional delay permissible before the /// job is executed. `nil` means no limit. /// - clock: The clock used for the delay. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) func enqueue(_ job: consuming ExecutorJob, after delay: C.Duration, tolerance: C.Duration?, @@ -83,7 +83,7 @@ public protocol SchedulableExecutor: Executor { /// - tolerance: The maximum additional delay permissible before the /// job is executed. `nil` means no limit. /// - clock: The clock used for the delay.. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) func enqueue(_ job: consuming ExecutorJob, at instant: C.Instant, tolerance: C.Duration?, @@ -117,7 +117,7 @@ extension Executor { /// Executors that implement SchedulableExecutor should provide their /// own copy of this method, which will allow the compiler to avoid a /// potentially expensive runtime cast. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) var asSchedulable: SchedulableExecutor? { return self as? SchedulableExecutor } @@ -140,19 +140,19 @@ extension Executor { #if !$Embedded // This defaults to `false` so that existing third-party Executor // implementations will work as expected. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public var isMainExecutor: Bool { false } #endif } // Delay support -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension SchedulableExecutor { #if !$Embedded && !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public func enqueue(_ job: consuming ExecutorJob, after delay: C.Duration, tolerance: C.Duration? = nil, @@ -163,7 +163,7 @@ extension SchedulableExecutor { tolerance: tolerance, clock: clock) } - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public func enqueue(_ job: consuming ExecutorJob, at instant: C.Instant, tolerance: C.Duration? = nil, @@ -267,7 +267,7 @@ public protocol SerialExecutor: Executor { // avoid drilling down to the base conformance just for the basic // work-scheduling operation. @_nonoverride - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) @available(*, deprecated, message: "Implement 'enqueue(_: consuming ExecutorJob)' instead") func enqueue(_ job: consuming Job) #endif // !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY @@ -278,7 +278,7 @@ public protocol SerialExecutor: Executor { // avoid drilling down to the base conformance just for the basic // work-scheduling operation. @_nonoverride - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) func enqueue(_ job: consuming ExecutorJob) #endif // !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY @@ -309,7 +309,7 @@ public protocol SerialExecutor: Executor { /// - Returns: `true`, if `self` and the `other` executor actually are /// mutually exclusive and it is safe–from a concurrency /// perspective–to execute code assuming one on the other. - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) func isSameExclusiveExecutionContext(other: Self) -> Bool /// Last resort "fallback" isolation check, called when the concurrency runtime @@ -332,7 +332,7 @@ public protocol SerialExecutor: Executor { /// /// - Warning: This method must crash and halt program execution if unable /// to prove the isolation of the calling context. - @available(SwiftStdlib 6.0, *) + @available(StdlibDeploymentTarget 6.0, *) func checkIsolated() /// Checks if the current execution context is isolated by this executor. @@ -352,20 +352,20 @@ public protocol SerialExecutor: Executor { /// The default implementation returns `nil` is used to indicate that it is "unknown" if the current context is /// isolated by this serial executor. The runtime then _may_ proceed to invoke `checkIsolated()` as a last-resort /// attempt to verify the isolation of the current context. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) func isIsolatingCurrentContext() -> Bool? } -@available(SwiftStdlib 6.0, *) +@available(StdlibDeploymentTarget 6.0, *) extension SerialExecutor { #if !$Embedded && !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public var isMainExecutor: Bool { return MainActor.executor._isSameExecutor(self) } #endif - @available(SwiftStdlib 6.0, *) + @available(StdlibDeploymentTarget 6.0, *) public func checkIsolated() { #if !$Embedded fatalError("Unexpected isolation context, expected to be executing on \(Self.self)") @@ -375,13 +375,13 @@ extension SerialExecutor { } #if SWIFT_CONCURRENCY_USES_DISPATCH - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) private var _dispatchQueue: OpaquePointer? { return unsafe _getDispatchQueueForExecutor(self.asUnownedSerialExecutor()) } #endif - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) internal func _isSameExecutor(_ rhs: some SerialExecutor) -> Bool { if rhs === self { return true @@ -401,10 +401,10 @@ extension SerialExecutor { } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension SerialExecutor { - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public func isIsolatingCurrentContext() -> Bool? { return nil } @@ -427,7 +427,7 @@ extension SerialExecutor { /// the provided task executor. /// /// Unstructured tasks do not inherit the task executor. -@available(SwiftStdlib 6.0, *) +@available(StdlibDeploymentTarget 6.0, *) public protocol TaskExecutor: Executor { // This requirement is repeated here as a non-override so that we // get a redundant witness-table entry for it. This allows us to @@ -458,7 +458,7 @@ public protocol TaskExecutor: Executor { func asUnownedTaskExecutor() -> UnownedTaskExecutor } -@available(SwiftStdlib 6.0, *) +@available(StdlibDeploymentTarget 6.0, *) extension TaskExecutor { public func asUnownedTaskExecutor() -> UnownedTaskExecutor { unsafe UnownedTaskExecutor(ordinary: self) @@ -466,7 +466,7 @@ extension TaskExecutor { } #if !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) extension Executor { // Delegation goes like this: @@ -486,28 +486,28 @@ extension Executor { } #endif // !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) extension SerialExecutor { - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) public func asUnownedSerialExecutor() -> UnownedSerialExecutor { unsafe UnownedSerialExecutor(ordinary: self) } } -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) extension SerialExecutor { - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) public func isSameExclusiveExecutionContext(other: Self) -> Bool { return self === other } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension SerialExecutor where Self: Equatable { - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public func isSameExclusiveExecutionContext(other: Self) -> Bool { return self == other } @@ -519,7 +519,7 @@ extension SerialExecutor where Self: Equatable { /// The idea here is that some executors may work by running a loop /// that processes events of some sort; we want a way to enter that loop, /// and we would also like a way to trigger the loop to exit. -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public protocol RunLoopExecutor: Executor { /// Run the executor's run loop. /// @@ -550,7 +550,7 @@ public protocol RunLoopExecutor: Executor { func stop() } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension RunLoopExecutor { public func runUntil(_ condition: () -> Bool) throws { @@ -562,14 +562,14 @@ extension RunLoopExecutor { /// The main executor must conform to these three protocols; we have to /// make this a protocol for compatibility with Embedded Swift. -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public protocol MainExecutor: RunLoopExecutor, SerialExecutor { } /// An ExecutorFactory is used to create the default main and task /// executors. -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public protocol ExecutorFactory { #if !$Embedded /// Constructs and returns the main executor, which is started implicitly @@ -582,10 +582,10 @@ public protocol ExecutorFactory { static var defaultExecutor: any TaskExecutor { get } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) typealias DefaultExecutorFactory = PlatformExecutorFactory -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_createExecutors") public func _createExecutors(factory: F.Type) { #if !$Embedded && !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY @@ -604,7 +604,7 @@ func _createDefaultExecutors() { #if !$Embedded && !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY extension MainActor { - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) static var _executor: (any MainExecutor)? = nil /// The main executor, which is started implicitly by the `async main` @@ -612,7 +612,7 @@ extension MainActor { /// /// Attempting to set this after the first `enqueue` on the main /// executor is a fatal error. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public static var executor: any MainExecutor { // It would be good if there was a Swift way to do this _createDefaultExecutorsOnce() @@ -622,7 +622,7 @@ extension MainActor { #endif // !$Embedded && !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY extension Task where Success == Never, Failure == Never { - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) static var _defaultExecutor: (any TaskExecutor)? = nil /// The default or global executor, which is the default place in which @@ -630,7 +630,7 @@ extension Task where Success == Never, Failure == Never { /// /// Attempting to set this after the first `enqueue` on the global /// executor is a fatal error. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public static var defaultExecutor: any TaskExecutor { // It would be good if there was a Swift way to do this _createDefaultExecutorsOnce() @@ -650,7 +650,7 @@ extension Task where Success == Never, Failure == Never { /// 3. The task executor for the current thread /// /// If none of these exist, returns the default executor. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) @_unavailableInEmbedded public static var currentExecutor: any Executor { if let activeExecutor = unsafe _getActiveExecutor().asSerialExecutor() { @@ -664,7 +664,7 @@ extension Task where Success == Never, Failure == Never { } /// Get the preferred executor for the current `Task`, if any. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public static var preferredExecutor: (any TaskExecutor)? { if let taskExecutor = unsafe _getPreferredTaskExecutor().asTaskExecutor() { return taskExecutor @@ -676,7 +676,7 @@ extension Task where Success == Never, Failure == Never { /// /// This follows the same logic as `currentExecutor`, except that it ignores /// any executor that isn't a `SchedulableExecutor`. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) @_unavailableInEmbedded public static var currentSchedulableExecutor: (any SchedulableExecutor)? { if let activeExecutor = unsafe _getActiveExecutor().asSerialExecutor(), @@ -768,14 +768,14 @@ public struct UnownedSerialExecutor: Sendable { unsafe _executor_isComplexEquality(self) } - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public func asSerialExecutor() -> (any SerialExecutor)? { return unsafe unsafeBitCast(executor, to: (any SerialExecutor)?.self) } } -@available(SwiftStdlib 6.0, *) +@available(StdlibDeploymentTarget 6.0, *) @unsafe @frozen public struct UnownedTaskExecutor: Sendable { @@ -805,7 +805,7 @@ public struct UnownedTaskExecutor: Sendable { unsafe self.executor = Builtin.buildOrdinaryTaskExecutorRef(executor) } - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public func asTaskExecutor() -> (any TaskExecutor)? { return unsafe unsafeBitCast(executor, to: (any TaskExecutor)?.self) } @@ -868,7 +868,7 @@ func _checkExpectedExecutor(_filenameStart: Builtin.RawPointer, /// otherwise returns only the job's 32bit Id. /// /// - Returns: the Id stored in this ExecutorJob or Task, for purposes of debug printing -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) @_silgen_name("swift_task_getJobTaskId") internal func _getJobTaskId(_ job: UnownedJob) -> UInt64 @@ -922,10 +922,10 @@ internal func _task_taskExecutor_getTaskExecutorRef(_ taskExecutor: E) -> Bui internal func _enqueueOnExecutor(job unownedJob: UnownedJob, executor: E) where E: SerialExecutor { #if !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY - if #available(SwiftStdlib 5.9, *) { + if #available(StdlibDeploymentTarget 5.9, *) { executor.enqueue(ExecutorJob(context: unownedJob._context)) } else { - executor.enqueue(unownedJob) + fatalError("we shouldn't get here; if we have, availability is broken") } #else // SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY executor.enqueue(unownedJob) diff --git a/stdlib/public/Concurrency/ExecutorBridge.swift b/stdlib/public/Concurrency/ExecutorBridge.swift index 6d378616d4591..5c34b8febf4a1 100644 --- a/stdlib/public/Concurrency/ExecutorBridge.swift +++ b/stdlib/public/Concurrency/ExecutorBridge.swift @@ -17,19 +17,19 @@ import Swift -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("_swift_exit") internal func _exit(result: CInt) #if !$Embedded -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("_swift_task_isMainExecutorSwift") internal func _isMainExecutor(_ executor: E) -> Bool where E: SerialExecutor { return executor.isMainExecutor } #endif -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("_swift_task_checkIsolatedSwift") internal func checkIsolated(executor: E) where E: SerialExecutor { executor.checkIsolated() @@ -40,7 +40,7 @@ internal func checkIsolated(executor: E) where E: SerialExecutor { /// -1: unknown /// 0: not isolated /// 1: isolated -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("_swift_task_isIsolatingCurrentContextSwift") internal func isIsolatingCurrentContext(executor: E) -> Int8 where E: SerialExecutor { @@ -51,37 +51,37 @@ internal func isIsolatingCurrentContext(executor: E) -> Int8 } } -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("_swift_getActiveExecutor") internal func _getActiveExecutor() -> UnownedSerialExecutor -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("_swift_getCurrentTaskExecutor") internal func _getCurrentTaskExecutor() -> UnownedTaskExecutor -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("_swift_getPreferredTaskExecutor") internal func _getPreferredTaskExecutor() -> UnownedTaskExecutor -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_job_allocate") internal func _jobAllocate(_ job: Builtin.Job, _ capacity: Int) -> UnsafeMutableRawPointer -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_job_deallocate") internal func _jobDeallocate(_ job: Builtin.Job, _ address: UnsafeMutableRawPointer) -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_job_getPriority") internal func _jobGetPriority(_ job: Builtin.Job) -> UInt8 -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_job_getKind") internal func _jobGetKind(_ job: Builtin.Job) -> UInt8 -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_job_getExecutorPrivateData") internal func _jobGetExecutorPrivateData( _ job: Builtin.Job @@ -89,32 +89,32 @@ internal func _jobGetExecutorPrivateData( #if !$Embedded #if !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_getMainExecutor") internal func _getMainExecutorAsSerialExecutor() -> (any SerialExecutor)? { return MainActor.executor } #else // For task-to-thread model, this is implemented in C++ -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_getMainExecutor") internal func _getMainExecutorAsSerialExecutor() -> (any SerialExecutor)? #endif // SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY #endif // !$Embedded -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_dispatchMain") internal func _dispatchMain() -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_dispatchEnqueueMain") internal func _dispatchEnqueueMain(_ job: UnownedJob) -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_dispatchEnqueueGlobal") internal func _dispatchEnqueueGlobal(_ job: UnownedJob) -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_dispatchEnqueueWithDeadline") internal func _dispatchEnqueueWithDeadline(_ global: CBool, _ sec: CLongLong, @@ -124,7 +124,7 @@ internal func _dispatchEnqueueWithDeadline(_ global: CBool, _ clock: CInt, _ job: UnownedJob) -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) @_silgen_name("swift_dispatchAssertMainQueue") internal func _dispatchAssertMainQueue() diff --git a/stdlib/public/Concurrency/GlobalConcurrentExecutor.swift b/stdlib/public/Concurrency/GlobalConcurrentExecutor.swift index 36b57920e56bf..c8e0a0a4a54db 100644 --- a/stdlib/public/Concurrency/GlobalConcurrentExecutor.swift +++ b/stdlib/public/Concurrency/GlobalConcurrentExecutor.swift @@ -34,10 +34,10 @@ import Swift @_unavailableInEmbedded public var globalConcurrentExecutor: any TaskExecutor { get { - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { return Task.defaultExecutor } else { - return _DefaultGlobalConcurrentExecutor.shared + fatalError("we shouldn't get here; if we have, availability is broken") } } } diff --git a/stdlib/public/Concurrency/PartialAsyncTask.swift b/stdlib/public/Concurrency/PartialAsyncTask.swift index 952c601ec1935..deb47cf9445fb 100644 --- a/stdlib/public/Concurrency/PartialAsyncTask.swift +++ b/stdlib/public/Concurrency/PartialAsyncTask.swift @@ -33,14 +33,14 @@ internal func _swiftJobRun(_ job: UnownedJob, _ executor: UnownedSerialExecutor) -> () @_unavailableInEmbedded -@available(SwiftStdlib 6.0, *) +@available(StdlibDeploymentTarget 6.0, *) @_silgen_name("swift_job_run_on_task_executor") @usableFromInline internal func _swiftJobRunOnTaskExecutor(_ job: UnownedJob, _ executor: UnownedTaskExecutor) -> () @_unavailableInEmbedded -@available(SwiftStdlib 6.0, *) +@available(StdlibDeploymentTarget 6.0, *) @_silgen_name("swift_job_run_on_serial_and_task_executor") @usableFromInline internal func _swiftJobRunOnTaskExecutor(_ job: UnownedJob, @@ -63,14 +63,14 @@ public struct UnownedJob: Sendable { private var context: Builtin.Job @usableFromInline - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) internal init(context: Builtin.Job) { self.context = context } #if !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY /// Create an `UnownedJob` whose lifetime must be managed carefully until it is run exactly once. - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) public init(_ job: __owned Job) { // must remain '__owned' in order to not break ABI self.context = job.context } @@ -78,27 +78,25 @@ public struct UnownedJob: Sendable { #if !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY /// Create an `UnownedJob` whose lifetime must be managed carefully until it is run exactly once. - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) public init(_ job: __owned ExecutorJob) { // must remain '__owned' in order to not break ABI self.context = job.context } #endif // !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY /// The priority of this job. - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) public var priority: JobPriority { let raw: UInt8 - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { raw = _jobGetPriority(context) } else { - // Since we're building the new version of the stdlib, we should - // never get here. - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } return JobPriority(rawValue: raw) } - @available(SwiftStdlib 5.9, *) + @available(StdlibDeploymentTarget 5.9, *) internal var _context: Builtin.Job { context } @@ -145,7 +143,7 @@ public struct UnownedJob: Sendable { /// /// - SeeAlso: ``runSynchronously(isolatedTo:taskExecutor:)`` @_unavailableInEmbedded - @available(SwiftStdlib 6.0, *) + @available(StdlibDeploymentTarget 6.0, *) @_alwaysEmitIntoClient @inlinable public func runSynchronously(on executor: UnownedTaskExecutor) { @@ -173,7 +171,7 @@ public struct UnownedJob: Sendable { /// /// - SeeAlso: ``runSynchronously(on:)`` @_unavailableInEmbedded - @available(SwiftStdlib 6.0, *) + @available(StdlibDeploymentTarget 6.0, *) @_alwaysEmitIntoClient @inlinable public func runSynchronously(isolatedTo serialExecutor: UnownedSerialExecutor, @@ -208,7 +206,7 @@ extension UnownedJob: CustomStringConvertible { /// /// Unless you're implementing a scheduler, /// you don't generally interact with jobs directly. -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) @available(*, deprecated, renamed: "ExecutorJob") @frozen public struct Job: Sendable, ~Copyable { @@ -229,12 +227,10 @@ public struct Job: Sendable, ~Copyable { public var priority: JobPriority { let raw: UInt8 - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { raw = _jobGetPriority(self.context) } else { - // We are building the new version of the code, so we should never - // get here. - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } return JobPriority(rawValue: raw) } @@ -284,7 +280,7 @@ extension Job { /// /// Unless you're implementing a scheduler, /// you don't generally interact with jobs directly. -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) @frozen public struct ExecutorJob: Sendable, ~Copyable { internal var context: Builtin.Job @@ -304,12 +300,10 @@ public struct ExecutorJob: Sendable, ~Copyable { public var priority: JobPriority { let raw: UInt8 - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { raw = _jobGetPriority(self.context) } else { - // We are building the new version of the code, so we should never - // get here. - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } return JobPriority(rawValue: raw) } @@ -322,7 +316,7 @@ public struct ExecutorJob: Sendable, ~Copyable { /// - body: The closure to execute. /// /// Returns the result of executing the closure. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public func withUnsafeExecutorPrivateData(body: (UnsafeMutableRawBufferPointer) throws(E) -> R) throws(E) -> R { let base = _jobGetExecutorPrivateData(self.context) let size = unsafe 2 * MemoryLayout.stride @@ -331,7 +325,7 @@ public struct ExecutorJob: Sendable, ~Copyable { } /// Kinds of schedulable jobs - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) @frozen public struct Kind: Sendable, RawRepresentable { public typealias RawValue = UInt8 @@ -352,7 +346,7 @@ public struct ExecutorJob: Sendable, ~Copyable { } /// What kind of job this is. - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public var kind: Kind { return Kind(rawValue: _jobGetKind(self.context))! } @@ -373,7 +367,7 @@ public struct ExecutorJob: Sendable, ~Copyable { } } -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) extension ExecutorJob { /// Run this job on the passed in executor. @@ -415,7 +409,7 @@ extension ExecutorJob { /// /// - SeeAlso: ``runSynchronously(isolatedTo:taskExecutor:)`` @_unavailableInEmbedded - @available(SwiftStdlib 6.0, *) + @available(StdlibDeploymentTarget 6.0, *) @_alwaysEmitIntoClient @inlinable __consuming public func runSynchronously(on executor: UnownedTaskExecutor) { @@ -438,7 +432,7 @@ extension ExecutorJob { /// /// - SeeAlso: ``runSynchronously(on:)`` @_unavailableInEmbedded - @available(SwiftStdlib 6.0, *) + @available(StdlibDeploymentTarget 6.0, *) @_alwaysEmitIntoClient @inlinable __consuming public func runSynchronously(isolatedTo serialExecutor: UnownedSerialExecutor, @@ -448,7 +442,7 @@ extension ExecutorJob { } // Stack-disciplined job-local allocator support -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) extension ExecutorJob { /// Obtain a stack-disciplined job-local allocator. @@ -539,7 +533,7 @@ extension ExecutorJob { /// however, since not all jobs are tasks, represented as separate type. /// /// Conversions between the two priorities are available as initializers on the respective types. -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) @frozen public struct JobPriority: Sendable { public typealias RawValue = UInt8 @@ -563,7 +557,7 @@ extension TaskPriority { } } -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) extension JobPriority: Equatable { public static func == (lhs: JobPriority, rhs: JobPriority) -> Bool { lhs.rawValue == rhs.rawValue @@ -574,7 +568,7 @@ extension JobPriority: Equatable { } } -@available(SwiftStdlib 5.9, *) +@available(StdlibDeploymentTarget 5.9, *) extension JobPriority: Comparable { public static func < (lhs: JobPriority, rhs: JobPriority) -> Bool { lhs.rawValue < rhs.rawValue diff --git a/stdlib/public/Concurrency/PlatformExecutorCooperative.swift b/stdlib/public/Concurrency/PlatformExecutorCooperative.swift index 5c17e1d2ba084..e9288bfc7cdd7 100644 --- a/stdlib/public/Concurrency/PlatformExecutorCooperative.swift +++ b/stdlib/public/Concurrency/PlatformExecutorCooperative.swift @@ -13,7 +13,7 @@ import Swift // This platform uses a single, global, CooperativeExecutor -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public struct PlatformExecutorFactory: ExecutorFactory { static let executor = CooperativeExecutor() public static var mainExecutor: any MainExecutor { executor } diff --git a/stdlib/public/Concurrency/PlatformExecutorDarwin.swift b/stdlib/public/Concurrency/PlatformExecutorDarwin.swift index 90017beb45106..71cf93d92f879 100644 --- a/stdlib/public/Concurrency/PlatformExecutorDarwin.swift +++ b/stdlib/public/Concurrency/PlatformExecutorDarwin.swift @@ -14,7 +14,7 @@ import Swift -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public struct PlatformExecutorFactory: ExecutorFactory { public static var mainExecutor: any MainExecutor { if CoreFoundation.isPresent { diff --git a/stdlib/public/Concurrency/PlatformExecutorLinux.swift b/stdlib/public/Concurrency/PlatformExecutorLinux.swift index a14c492c8ab59..19d245a1a7e6e 100644 --- a/stdlib/public/Concurrency/PlatformExecutorLinux.swift +++ b/stdlib/public/Concurrency/PlatformExecutorLinux.swift @@ -15,7 +15,7 @@ import Swift // The default executors for now are Dispatch-based -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public struct PlatformExecutorFactory: ExecutorFactory { public static let mainExecutor: any MainExecutor = DispatchMainExecutor() public static let defaultExecutor: any TaskExecutor diff --git a/stdlib/public/Concurrency/PlatformExecutorNone.swift b/stdlib/public/Concurrency/PlatformExecutorNone.swift index ed03e536c0915..c052893f5413a 100644 --- a/stdlib/public/Concurrency/PlatformExecutorNone.swift +++ b/stdlib/public/Concurrency/PlatformExecutorNone.swift @@ -12,7 +12,7 @@ import Swift -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public struct PlatformExecutorFactory: ExecutorFactory { public static let mainExecutor: any MainExecutor = UnimplementedMainExecutor() public static let defaultExecutor: any TaskExecutor = UnimplementedTaskExecutor() diff --git a/stdlib/public/Concurrency/PlatformExecutorWindows.swift b/stdlib/public/Concurrency/PlatformExecutorWindows.swift index e64665a94da37..08ec70519931c 100644 --- a/stdlib/public/Concurrency/PlatformExecutorWindows.swift +++ b/stdlib/public/Concurrency/PlatformExecutorWindows.swift @@ -15,7 +15,7 @@ import Swift // The default executors for now are Dispatch-based -@available(SwiftStdlib 6.2, *) +@available(StdlibDeploymentTarget 6.2, *) public struct PlatformExecutorFactory: ExecutorFactory { public static let mainExecutor: any MainExecutor = DispatchMainExecutor() public static let defaultExecutor: any TaskExecutor = diff --git a/stdlib/public/Concurrency/SuspendingClock.swift b/stdlib/public/Concurrency/SuspendingClock.swift index cec63ed99f55e..78443708f2fec 100644 --- a/stdlib/public/Concurrency/SuspendingClock.swift +++ b/stdlib/public/Concurrency/SuspendingClock.swift @@ -20,7 +20,7 @@ import Swift /// only comparable on the same machine in the same booted session. /// /// This clock is suitable for high resolution measurements of execution. -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded public struct SuspendingClock: Sendable { public struct Instant: Sendable { @@ -35,12 +35,12 @@ public struct SuspendingClock: Sendable { } #if !$Embedded -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension SuspendingClock.Instant: Codable { } #endif -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded extension Clock where Self == SuspendingClock { /// A clock that measures time that always increments but stops incrementing @@ -48,21 +48,21 @@ extension Clock where Self == SuspendingClock { /// /// try await Task.sleep(until: .now + .seconds(3), clock: .suspending) /// - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static var suspending: SuspendingClock { return SuspendingClock() } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded extension SuspendingClock: Clock { /// The current instant accounting for machine suspension. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public var now: SuspendingClock.Instant { SuspendingClock.now } /// The current instant accounting for machine suspension. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static var now: SuspendingClock.Instant { var seconds = Int64(0) var nanoseconds = Int64(0) @@ -76,7 +76,7 @@ extension SuspendingClock: Clock { } /// The minimum non-zero resolution between any two calls to `now`. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public var minimumResolution: Swift.Duration { var seconds = Int64(0) var nanoseconds = Int64(0) @@ -88,7 +88,7 @@ extension SuspendingClock: Clock { } /// The suspending clock is monotonic - @available(SwiftStdlib 6.2, *) + @available(StdlibDeploymentTarget 6.2, *) public var traits: ClockTraits { return [.monotonic] } @@ -103,21 +103,20 @@ extension SuspendingClock: Clock { /// `CancellationError`. /// /// This function doesn't block the underlying thread. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public func sleep( until deadline: Instant, tolerance: Swift.Duration? = nil ) async throws { - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { try await Task._sleep(until: deadline, tolerance: tolerance, clock: self) } else { - // Should never see this - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } } #else - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) @available(*, unavailable, message: "Unavailable in task-to-thread concurrency model") public func sleep( until deadline: Instant, tolerance: Swift.Duration? = nil @@ -127,70 +126,59 @@ extension SuspendingClock: Clock { #endif } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded extension SuspendingClock.Instant: InstantProtocol { - @available(SwiftStdlib 5.7, *) public static var now: SuspendingClock.Instant { SuspendingClock().now } - @available(SwiftStdlib 5.7, *) public func advanced(by duration: Swift.Duration) -> SuspendingClock.Instant { SuspendingClock.Instant(_value: _value + duration) } - @available(SwiftStdlib 5.7, *) public func duration(to other: SuspendingClock.Instant) -> Swift.Duration { other._value - _value } - @available(SwiftStdlib 5.7, *) public func hash(into hasher: inout Hasher) { hasher.combine(_value) } - @available(SwiftStdlib 5.7, *) public static func == ( _ lhs: SuspendingClock.Instant, _ rhs: SuspendingClock.Instant ) -> Bool { return lhs._value == rhs._value } - @available(SwiftStdlib 5.7, *) public static func < ( _ lhs: SuspendingClock.Instant, _ rhs: SuspendingClock.Instant ) -> Bool { return lhs._value < rhs._value } - @available(SwiftStdlib 5.7, *) public static func + ( _ lhs: SuspendingClock.Instant, _ rhs: Swift.Duration ) -> SuspendingClock.Instant { lhs.advanced(by: rhs) } - @available(SwiftStdlib 5.7, *) public static func += ( _ lhs: inout SuspendingClock.Instant, _ rhs: Swift.Duration ) { lhs = lhs.advanced(by: rhs) } - @available(SwiftStdlib 5.7, *) public static func - ( _ lhs: SuspendingClock.Instant, _ rhs: Swift.Duration ) -> SuspendingClock.Instant { lhs.advanced(by: .zero - rhs) } - @available(SwiftStdlib 5.7, *) public static func -= ( _ lhs: inout SuspendingClock.Instant, _ rhs: Swift.Duration ) { lhs = lhs.advanced(by: .zero - rhs) } - @available(SwiftStdlib 5.7, *) public static func - ( _ lhs: SuspendingClock.Instant, _ rhs: SuspendingClock.Instant ) -> Swift.Duration { diff --git a/stdlib/public/Concurrency/Task.swift b/stdlib/public/Concurrency/Task.swift index 3a23bfe1f1558..01baf08d325ca 100644 --- a/stdlib/public/Concurrency/Task.swift +++ b/stdlib/public/Concurrency/Task.swift @@ -637,12 +637,12 @@ extension Task where Success == Never, Failure == Never { continuation: continuation) #if !$Embedded && !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { let executor = Task.currentExecutor executor.enqueue(ExecutorJob(context: job)) } else { - _enqueueJobGlobal(job) + fatalError("we shouldn't get here; if we have, availability is broken") } #else _enqueueJobGlobal(job) @@ -822,7 +822,7 @@ func _enqueueJobGlobalWithDelay(_ delay: UInt64, _ task: UnownedJob) { return _enqueueJobGlobalWithDelay(delay, task._context) } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_silgen_name("swift_task_enqueueGlobalWithDeadline") @usableFromInline func _enqueueJobGlobalWithDeadline(_ seconds: Int64, _ nanoseconds: Int64, @@ -898,10 +898,10 @@ internal func _runAsyncMain(_ asyncFun: @Sendable @escaping () async throws -> ( } let job = Builtin.convertTaskToJob(theTask) - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { MainActor.executor.enqueue(ExecutorJob(context: job)) } else { - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } _asyncMainDrainQueue() diff --git a/stdlib/public/Concurrency/TaskSleep.swift b/stdlib/public/Concurrency/TaskSleep.swift index 653a343c546d8..c40483bfb4a70 100644 --- a/stdlib/public/Concurrency/TaskSleep.swift +++ b/stdlib/public/Concurrency/TaskSleep.swift @@ -28,7 +28,7 @@ extension Task where Success == Never, Failure == Never { priority: Int(Task.currentPriority.rawValue), continuation: continuation) - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { #if !$Embedded if let executor = Task.currentSchedulableExecutor { executor.enqueue(ExecutorJob(context: job), @@ -272,7 +272,7 @@ extension Task where Success == Never, Failure == Never { let job = Builtin.convertTaskToJob(sleepTask) - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { #if !$Embedded if let executor = Task.currentSchedulableExecutor { executor.enqueue(ExecutorJob(context: job), diff --git a/stdlib/public/Concurrency/TaskSleepDuration.swift b/stdlib/public/Concurrency/TaskSleepDuration.swift index d9e3876c69534..3bdf2f7618b75 100644 --- a/stdlib/public/Concurrency/TaskSleepDuration.swift +++ b/stdlib/public/Concurrency/TaskSleepDuration.swift @@ -13,18 +13,18 @@ import Swift #if !SWIFT_STDLIB_TASK_TO_THREAD_MODEL_CONCURRENCY -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) fileprivate func timestamp(for instant: C.Instant, clock: C) -> (clockID: _ClockID, seconds: Int64, nanoseconds: Int64) { var clockID: _ClockID - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { if clock.traits.contains(.continuous) { clockID = .continuous } else { clockID = .suspending } } else { - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } var seconds: Int64 = 0 @@ -34,10 +34,10 @@ fileprivate func timestamp(for instant: C.Instant, clock: C) clock: clockID.rawValue) let delta: Swift.Duration - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { delta = clock.convert(from: clock.now.duration(to: instant))! } else { - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } let (deltaSeconds, deltaAttoseconds) = delta.components @@ -54,10 +54,10 @@ fileprivate func timestamp(for instant: C.Instant, clock: C) nanoseconds: Int64(nanoseconds)) } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded extension Task where Success == Never, Failure == Never { - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) internal static func _sleep( until instant: C.Instant, tolerance: C.Duration?, @@ -97,7 +97,7 @@ extension Task where Success == Never, Failure == Never { let job = Builtin.convertTaskToJob(sleepTask) - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { #if !$Embedded if let executor = Task.currentSchedulableExecutor { executor.enqueue(ExecutorJob(context: job), @@ -108,7 +108,7 @@ extension Task where Success == Never, Failure == Never { } #endif } else { - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } // If there is no current schedulable executor, fall back to @@ -117,7 +117,7 @@ extension Task where Success == Never, Failure == Never { clock: clock) let toleranceSeconds: Int64 let toleranceNanoseconds: Int64 - if #available(SwiftStdlib 6.2, *) { + if #available(StdlibDeploymentTarget 6.2, *) { if let tolerance = tolerance, let components = clock.convert(from: tolerance)?.components { toleranceSeconds = components.seconds @@ -127,16 +127,16 @@ extension Task where Success == Never, Failure == Never { toleranceNanoseconds = -1 } } else { - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } - if #available(SwiftStdlib 5.9, *) { + if #available(StdlibDeploymentTarget 5.9, *) { _enqueueJobGlobalWithDeadline( seconds, nanoseconds, toleranceSeconds, toleranceNanoseconds, clockID.rawValue, UnownedJob(context: job)) } else { - Builtin.unreachable() + fatalError("we shouldn't get here; if we have, availability is broken") } return diff --git a/stdlib/public/Synchronization/CMakeLists.txt b/stdlib/public/Synchronization/CMakeLists.txt index e654cceeb0ed3..90c1e3dfb7a82 100644 --- a/stdlib/public/Synchronization/CMakeLists.txt +++ b/stdlib/public/Synchronization/CMakeLists.txt @@ -169,7 +169,7 @@ if(SWIFT_SHOULD_BUILD_EMBEDDED_STDLIB) if("${arch}" MATCHES "avr") continue() endif() - + set(SWIFT_SDK_embedded_ARCH_${arch}_MODULE "${mod}") set(SWIFT_SDK_embedded_LIB_SUBDIR "embedded") set(SWIFT_SDK_embedded_ARCH_${arch}_TRIPLE "${triple}") diff --git a/stdlib/public/Volatile/CMakeLists.txt b/stdlib/public/Volatile/CMakeLists.txt index bf08132740c2d..dd91f0fa88f52 100644 --- a/stdlib/public/Volatile/CMakeLists.txt +++ b/stdlib/public/Volatile/CMakeLists.txt @@ -40,7 +40,7 @@ if(SWIFT_SHOULD_BUILD_EMBEDDED_STDLIB) IS_SDK_OVERLAY IS_FRAGILE Volatile.swift - + SWIFT_COMPILE_FLAGS -Xcc -ffreestanding -enable-experimental-feature Embedded -parse-stdlib diff --git a/stdlib/public/core/Duration.swift b/stdlib/public/core/Duration.swift index 6b4ac94d17e46..8b0e15b2b914b 100644 --- a/stdlib/public/core/Duration.swift +++ b/stdlib/public/core/Duration.swift @@ -31,7 +31,7 @@ /// temporal measurement component; specifically leap seconds should be /// represented as an additional accessor since that is specific only to certain /// clock implementations. -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @frozen public struct Duration: Sendable { /// The low 64 bits of a 128-bit signed integer value counting attoseconds. @@ -86,13 +86,13 @@ public struct Duration: Sendable { } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Duration { /// The composite components of the `Duration`. /// /// This is intended for facilitating conversions to existing time types. The /// attoseconds value will not exceed 1e18 or be lower than -1e18. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public var components: (seconds: Int64, attoseconds: Int64) { let (seconds, attoseconds) = _attoseconds.dividedBy1e18() return (Int64(seconds), Int64(attoseconds)) @@ -129,7 +129,7 @@ extension Duration { } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Duration { /// Construct a `Duration` given a number of seconds represented as a /// `BinaryInteger`. @@ -137,7 +137,7 @@ extension Duration { /// let d: Duration = .seconds(77) /// /// - Returns: A `Duration` representing a given number of seconds. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) @inlinable public static func seconds(_ seconds: T) -> Duration { guard let high = Int64(exactly: seconds >> 64) else { fatalError() } @@ -170,7 +170,7 @@ extension Duration { /// let d: Duration = .seconds(22.93) /// /// - Returns: A `Duration` representing a given number of seconds. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func seconds(_ seconds: Double) -> Duration { Duration(seconds, scale: 1_000_000_000_000_000_000) } @@ -181,7 +181,7 @@ extension Duration { /// let d: Duration = .milliseconds(645) /// /// - Returns: A `Duration` representing a given number of milliseconds. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) @inlinable public static func milliseconds( _ milliseconds: T @@ -199,7 +199,7 @@ extension Duration { /// let d: Duration = .milliseconds(88.3) /// /// - Returns: A `Duration` representing a given number of milliseconds. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func milliseconds(_ milliseconds: Double) -> Duration { Duration(milliseconds, scale: 1_000_000_000_000_000) } @@ -210,7 +210,7 @@ extension Duration { /// let d: Duration = .microseconds(12) /// /// - Returns: A `Duration` representing a given number of microseconds. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) @inlinable public static func microseconds( _ microseconds: T @@ -228,7 +228,7 @@ extension Duration { /// let d: Duration = .microseconds(382.9) /// /// - Returns: A `Duration` representing a given number of microseconds. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func microseconds(_ microseconds: Double) -> Duration { Duration(microseconds, scale: 1_000_000_000_000) } @@ -239,7 +239,7 @@ extension Duration { /// let d: Duration = .nanoseconds(1929) /// /// - Returns: A `Duration` representing a given number of nanoseconds. - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) @inlinable public static func nanoseconds( _ nanoseconds: T @@ -263,10 +263,10 @@ extension Duration { } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded extension Duration: Codable { - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public init(from decoder: Decoder) throws { var container = try decoder.unkeyedContainer() let high = try container.decode(Int64.self) @@ -274,7 +274,7 @@ extension Duration: Codable { self.init(_high: high, low: low) } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public func encode(to encoder: Encoder) throws { var container = encoder.unkeyedContainer() try container.encode(_high) @@ -282,112 +282,112 @@ extension Duration: Codable { } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Duration: Hashable { - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public func hash(into hasher: inout Hasher) { hasher.combine(_attoseconds) } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Duration: Equatable { - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func == (_ lhs: Duration, _ rhs: Duration) -> Bool { return lhs._attoseconds == rhs._attoseconds } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Duration: Comparable { - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func < (_ lhs: Duration, _ rhs: Duration) -> Bool { return lhs._attoseconds < rhs._attoseconds } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Duration: AdditiveArithmetic { - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static var zero: Duration { Duration(_attoseconds: 0) } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func + (_ lhs: Duration, _ rhs: Duration) -> Duration { return Duration(_attoseconds: lhs._attoseconds + rhs._attoseconds) } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func - (_ lhs: Duration, _ rhs: Duration) -> Duration { return Duration(_attoseconds: lhs._attoseconds - rhs._attoseconds) } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func += (_ lhs: inout Duration, _ rhs: Duration) { lhs = lhs + rhs } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func -= (_ lhs: inout Duration, _ rhs: Duration) { lhs = lhs - rhs } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Duration { - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func / (_ lhs: Duration, _ rhs: Double) -> Duration { return Duration(_attoseconds: _Int128(Double(lhs._attoseconds) / rhs)) } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func /= (_ lhs: inout Duration, _ rhs: Double) { lhs = lhs / rhs } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func / ( _ lhs: Duration, _ rhs: T ) -> Duration { Duration(_attoseconds: lhs._attoseconds / _Int128(rhs)) } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func /= (_ lhs: inout Duration, _ rhs: T) { lhs = lhs / rhs } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func / (_ lhs: Duration, _ rhs: Duration) -> Double { Double(lhs._attoseconds) / Double(rhs._attoseconds) } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func * (_ lhs: Duration, _ rhs: Double) -> Duration { Duration(_attoseconds: _Int128(Double(lhs._attoseconds) * rhs)) } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func * ( _ lhs: Duration, _ rhs: T ) -> Duration { Duration(_attoseconds: lhs._attoseconds * _Int128(rhs)) } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func *= (_ lhs: inout Duration, _ rhs: T) { lhs = lhs * rhs } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) @_unavailableInEmbedded extension Duration: CustomStringConvertible { - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public var description: String { return (Double(_attoseconds) / 1e18).description + " seconds" } } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension Duration: DurationProtocol { } diff --git a/stdlib/public/core/DurationProtocol.swift b/stdlib/public/core/DurationProtocol.swift index 4d538f4932f71..50a83c6308e29 100644 --- a/stdlib/public/core/DurationProtocol.swift +++ b/stdlib/public/core/DurationProtocol.swift @@ -11,7 +11,7 @@ //===----------------------------------------------------------------------===// /// A type that defines a duration for a given `InstantProtocol` type. -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) public protocol DurationProtocol: Comparable, AdditiveArithmetic, Sendable { static func / (_ lhs: Self, _ rhs: Int) -> Self static func /= (_ lhs: inout Self, _ rhs: Int) @@ -21,14 +21,14 @@ public protocol DurationProtocol: Comparable, AdditiveArithmetic, Sendable { static func / (_ lhs: Self, _ rhs: Self) -> Double } -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) extension DurationProtocol { - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func /= (_ lhs: inout Self, _ rhs: Int) { lhs = lhs / rhs } - @available(SwiftStdlib 5.7, *) + @available(StdlibDeploymentTarget 5.7, *) public static func *= (_ lhs: inout Self, _ rhs: Int) { lhs = lhs * rhs } diff --git a/stdlib/public/core/Instant.swift b/stdlib/public/core/Instant.swift index baec28e430320..64f75486564ea 100644 --- a/stdlib/public/core/Instant.swift +++ b/stdlib/public/core/Instant.swift @@ -11,7 +11,7 @@ //===----------------------------------------------------------------------===// // A type that defines a specific point in time for a given `Clock`. -@available(SwiftStdlib 5.7, *) +@available(StdlibDeploymentTarget 5.7, *) public protocol InstantProtocol: Comparable, Hashable, Sendable { associatedtype Duration: DurationProtocol func advanced(by duration: Duration) -> Self diff --git a/test/Concurrency/custom_executor_enqueue_availability.swift b/test/Concurrency/custom_executor_enqueue_availability.swift index ed01516f9921d..27ed349bcde7e 100644 --- a/test/Concurrency/custom_executor_enqueue_availability.swift +++ b/test/Concurrency/custom_executor_enqueue_availability.swift @@ -26,10 +26,12 @@ final class OldExecutorOldStdlib: SerialExecutor { /// availability, since in this case the UnownedJob version needs to exist. @available(SwiftStdlib 5.1, *) final class BothExecutorOldStdlib: SerialExecutor { - func enqueue(_ job: UnownedJob) {} // expected-note{{'enqueue' declared here}} + func enqueue(_ job: UnownedJob) {} + // This no longer warns, because of the use of StdlibDeploymentTarget in the + // runtime. @available(SwiftStdlib 5.9, *) - func enqueue(_ job: __owned ExecutorJob) {} // expected-warning{{'Executor.enqueue(ExecutorJob)' will never be used, due to the presence of 'enqueue(UnownedJob)'}} + func enqueue(_ job: __owned ExecutorJob) {} func asUnownedSerialExecutor() -> UnownedSerialExecutor { UnownedSerialExecutor(ordinary: self) diff --git a/test/lit.cfg b/test/lit.cfg index f46a677487d96..f824949630a0f 100644 --- a/test/lit.cfg +++ b/test/lit.cfg @@ -530,11 +530,59 @@ def availability_macro_to_swift_abi_target_triple(macro): return stdlib_vers, '%s-%s-%s%s%s' % (run_cpu, run_vendor, run_os, os_vers, run_environment) +# Compare two version numbers +def version_gt(a, b): + a_int = list(map(int, a.split("."))) + b_int = list(map(int, b.split("."))) + vlen = max(len(a_int), len(b_int)) + if len(a_int) < vlen: + a_int += [0] * (vlen - len(a_int)) + if len(b_int) < vlen: + b_int += [0] * (vlen - len(b_int)) + return a_int > b_int + +# Returns a StdlibDeploymentTarget macro given a SwiftStdlib macro +def availability_macro_to_current(macro): + matches = re.search(r'^\s*SwiftStdlib\s+([0-9\.]*)\s*:\s*(.*)', macro) + if not matches: + return None + + stdlib_vers = matches.group(1) + orig_spec = matches.group(2) + + vers_by_platform = {} + for platform_vers in orig_spec.split(', '): + components = platform_vers.split(' ') + vers_by_platform[components[0]] = components[1] + + platform_name = { + 'macosx': 'macOS', + 'ios': 'iOS', + 'maccatalyst': 'iOS', + 'tvos': 'tvOS', + 'watchos': 'watchOS' + }.get(run_os) + + orig_vers = vers_by_platform.get(platform_name) + if orig_vers is not None and orig_vers != "9999": + ver = platform.mac_ver()[0] + + if version_gt(orig_vers, ver): + return f"StdlibDeploymentTarget {stdlib_vers}:{platform_name} {ver}" + + return f"StdlibDeploymentTarget {stdlib_vers}:{orig_spec}" + # Add availability macros to the default frontend/driver flags and create target # triple substitutions for each stdlib version. for macro in load_availability_macros(): config.swift_frontend_test_options += " -define-availability '{0}'".format(macro) config.swift_driver_test_options += " -Xfrontend -define-availability -Xfrontend '{0}'".format(macro) + + current_macro = availability_macro_to_current(macro) + if current_macro: + config.swift_frontend_test_options += " -define-availability '{0}'".format(current_macro) + config.swift_driver_test_options += " -Xfrontend -define-availability -Xfrontend '{0}'".format(current_macro) + (stdlib_vers, triple) = availability_macro_to_swift_abi_target_triple(macro) config.substitutions.append(('%target-swift-{}-abi-triple'.format(stdlib_vers), triple)) diff --git a/utils/availability-macros.def b/utils/availability-macros.def index f816acd10afec..fedb4cbbfd9bb 100644 --- a/utils/availability-macros.def +++ b/utils/availability-macros.def @@ -15,6 +15,14 @@ # Each of the remaining lines must define an availability macro in the same # format used by the `-define-availability` frontend command line option. +# NOTE: The build system will define another macro, StdlibDeploymentTarget, for +# each SwiftStdlib macro defined in this file. The difference between the +# two is the the StdlibDeploymentTarget macro will never be set to a +# higher version than the machine on which we are building. +# +# This is to allow for use of new functions and types within the standard +# libraries, in such a way that these usages will work on our CI machines. + # 9999 is the generic unknown future Swift release. It always needs to resolve # to the special placeholder version numbers 9999. diff --git a/utils/build-script-impl b/utils/build-script-impl index 6e538161f83c4..6cfe2d98b51ca 100755 --- a/utils/build-script-impl +++ b/utils/build-script-impl @@ -216,6 +216,7 @@ KNOWN_SETTINGS=( swift-runtime-enable-leak-checker "0" "Enable leaks checking routines in the runtime" swift-stdlib-enable-assertions "1" "enable assertions in Swift" swift-stdlib-enable-debug-preconditions-in-release "0" "Enable _debugPrecondition checks in the stdlib in Release configurations" + swift-stdlib-enable-strict-availability "0" "enable strict availability checking in the stdlib" swift-tools-enable-lto "" "enable LTO compilation of Swift tools. *NOTE* This does not include the swift standard library and runtime. Must be set to one of 'thin' or 'full'" extra-swift-args "" "Extra arguments to pass to swift modules which match regex. Assumed to be a flattened cmake list consisting of [module_regexp, args, module_regexp, args, ...]" report-statistics "0" "set to 1 to generate compilation statistics files for swift libraries" @@ -1759,6 +1760,7 @@ for host in "${ALL_HOSTS[@]}"; do -DSWIFT_STDLIB_BUILD_TYPE:STRING="${SWIFT_STDLIB_BUILD_TYPE}" -DSWIFT_STDLIB_ASSERTIONS:BOOL=$(true_false "${SWIFT_STDLIB_ENABLE_ASSERTIONS}") -DSWIFT_STDLIB_ENABLE_DEBUG_PRECONDITIONS_IN_RELEASE=$(true_false "${SWIFT_STDLIB_ENABLE_DEBUG_PRECONDITIONS_IN_RELEASE}") + -DSWIFT_STDLIB_ENABLE_STRICT_AVAILABILITY:BOOL=$(true_false "${SWIFT_STDLIB_ENABLE_STRICT_AVAILABILITY}") -DSWIFT_ENABLE_DISPATCH:BOOL=$(true_false "${SWIFT_ENABLE_DISPATCH}") -DSWIFT_IMPLICIT_CONCURRENCY_IMPORT:BOOL=$(true_false "${SWIFT_IMPLICIT_CONCURRENCY_IMPORT}") -DSWIFT_STDLIB_SUPPORT_BACK_DEPLOYMENT:BOOL=$(true_false "${SWIFT_STDLIB_SUPPORT_BACK_DEPLOYMENT}") @@ -1943,6 +1945,13 @@ for host in "${ALL_HOSTS[@]}"; do ) fi + if [ "${SWIFT_FREESTANDING_AVAILABILITY_NAME}" ] ; then + cmake_options=( + "${cmake_options[@]}" + -DSWIFT_FREESTANDING_TRIPLE_NAME:STRING="${SWIFT_FREESTANDING_TRIPLE_NAME}" + ) + fi + if [ "${SWIFT_FREESTANDING_MODULE_NAME}" ] ; then cmake_options=( "${cmake_options[@]}" diff --git a/utils/build_swift/build_swift/driver_arguments.py b/utils/build_swift/build_swift/driver_arguments.py index b5607775e73d0..2b7d6d0779911 100644 --- a/utils/build_swift/build_swift/driver_arguments.py +++ b/utils/build_swift/build_swift/driver_arguments.py @@ -129,6 +129,9 @@ def _apply_default_arguments(args): if args.lldb_assertions is None: args.lldb_assertions = args.assertions + if args.swift_stdlib_strict_availability is None: + args.swift_stdlib_strict_availability = False + # --ios-all etc are not supported by open-source Swift. if args.ios_all: raise ValueError('error: --ios-all is unavailable in open-source ' @@ -1029,6 +1032,14 @@ def create_argument_parser(): const=False, help='disable assertions in llbuild') + option('--swift-stdlib-strict-availability', store, + const=True, + help='enable strict availability checking in the Swift standard library (you want this OFF for CI or at-desk builds)') + option('--no-swift-stdlib-strict-availability', + store('swift_stdlib_strict_availability'), + const=False, + help='disable strict availability checking in the Swift standard library (you want this OFF for CI or at-desk builds)') + # ------------------------------------------------------------------------- in_group('Select the CMake generator') diff --git a/utils/build_swift/tests/build_swift/test_driver_arguments.py b/utils/build_swift/tests/build_swift/test_driver_arguments.py index 70d3a521fd0d8..cb21dd3db6cb6 100644 --- a/utils/build_swift/tests/build_swift/test_driver_arguments.py +++ b/utils/build_swift/tests/build_swift/test_driver_arguments.py @@ -515,6 +515,10 @@ def test_option_watchos_all(self): with self.assertRaises(ValueError): self.parse_default_args(['--watchos-all']) + def test_swift_stdlib_strict_availability(self): + self.parse_default_args('--swift-stdlib-strict-availability') + self.parse_default_args('--no-swift-stdlib-strict-availability') + # ------------------------------------------------------------------------- # Implied defaults tests diff --git a/utils/build_swift/tests/expected_options.py b/utils/build_swift/tests/expected_options.py index d81c82b729d3d..f8d1a3526ed76 100644 --- a/utils/build_swift/tests/expected_options.py +++ b/utils/build_swift/tests/expected_options.py @@ -270,6 +270,7 @@ 'swift_profile_instr_use': None, 'swift_runtime_fixed_backtracer_path': None, 'swift_stdlib_assertions': True, + 'swift_stdlib_strict_availability': False, 'swift_stdlib_build_variant': 'Debug', 'swift_tools_ld64_lto_codegen_only_for_supporting_targets': False, 'swift_tools_max_parallel_lto_link_jobs': @@ -549,6 +550,10 @@ class BuildScriptImplOption(_BaseOption): SetOption('--skip-test-early-swift-driver', dest='test_early_swift_driver', value=False), + SetOption('--swift-stdlib-strict-availability', value=True), + SetOption('--no-swift-stdlib-strict-availability', + dest='swift_stdlib_strict_availability', value=False), + SetFalseOption('--no-llvm-include-tests', dest='llvm_include_tests'), SetTrueOption('--install-back-deploy-concurrency', diff --git a/utils/swift_build_support/swift_build_support/build_script_invocation.py b/utils/swift_build_support/swift_build_support/build_script_invocation.py index 30f2f29e930a8..a0289515fd039 100644 --- a/utils/swift_build_support/swift_build_support/build_script_invocation.py +++ b/utils/swift_build_support/swift_build_support/build_script_invocation.py @@ -108,6 +108,8 @@ def convert_to_impl_arguments(self): "--swift-enable-assertions", str(args.swift_assertions).lower(), "--swift-stdlib-enable-assertions", str( args.swift_stdlib_assertions).lower(), + "--swift-stdlib-enable-strict-availability", str( + args.swift_stdlib_strict_availability).lower(), "--swift-analyze-code-coverage", str( args.swift_analyze_code_coverage).lower(), "--llbuild-enable-assertions", str( diff --git a/utils/swift_build_support/swift_build_support/products/minimalstdlib.py b/utils/swift_build_support/swift_build_support/products/minimalstdlib.py index 38f0b73402f7b..276ed8020107d 100644 --- a/utils/swift_build_support/swift_build_support/products/minimalstdlib.py +++ b/utils/swift_build_support/swift_build_support/products/minimalstdlib.py @@ -67,8 +67,12 @@ def build(self, host_target): self.cmake_options.define( 'SWIFT_FREESTANDING_MODULE_NAME:STRING', 'macos') self.cmake_options.define('SWIFT_FREESTANDING_SDK:STRING', 'macosx') + self.cmake_options.define('SWIFT_FREESTANDING_DEPLOYMENT_VERSION:STRING', + '11.0') self.cmake_options.define( 'SWIFT_FREESTANDING_TRIPLE_NAME:STRING', 'macosx11.0') + self.cmake_options.define( + 'SWIFT_FREESTANDING_AVAILABILITY_NAME:STRING', 'macOS') self.cmake_options.define( 'SWIFT_PRIMARY_VARIANT_ARCH:STRING', 'x86_64') self.cmake_options.define(