Merge pull request #21611 from weissi/jw-make-urbp-contiguous
conform Unsafe(Mutable)RawBufferPointer conform to _HasContiguousBytes
diff --git a/cmake/modules/AddSwift.cmake b/cmake/modules/AddSwift.cmake
index a9165aa..c0869b9 100644
--- a/cmake/modules/AddSwift.cmake
+++ b/cmake/modules/AddSwift.cmake
@@ -2015,10 +2015,19 @@
WORLD_READ)
endif()
- swift_install_in_component("${SWIFTLIB_INSTALL_IN_COMPONENT}"
- FILES "${UNIVERSAL_LIBRARY_NAME}"
- DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/${resource_dir}/${resource_dir_sdk_subdir}"
+ if(sdk STREQUAL WINDOWS AND CMAKE_SYSTEM_NAME STREQUAL Windows)
+ swift_install_in_component("${SWIFTLIB_INSTALL_IN_COMPONENT}"
+ TARGETS ${name}-windows-${SWIFT_PRIMARY_VARIANT_ARCH}
+ RUNTIME DESTINATION "bin"
+ LIBRARY DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/${resource_dir}/${resource_dir_sdk_subdir}"
+ ARCHIVE DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/${resource_dir}/${resource_dir_sdk_subdir}"
PERMISSIONS ${file_permissions})
+ else()
+ swift_install_in_component("${SWIFTLIB_INSTALL_IN_COMPONENT}"
+ FILES "${UNIVERSAL_LIBRARY_NAME}"
+ DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/${resource_dir}/${resource_dir_sdk_subdir}"
+ PERMISSIONS ${file_permissions})
+ endif()
if(sdk STREQUAL WINDOWS)
foreach(arch ${SWIFT_SDK_WINDOWS_ARCHITECTURES})
if(TARGET ${name}-windows-${arch}_IMPLIB)
diff --git a/docs/WindowsBuild.md b/docs/WindowsBuild.md
index 043a41e..0bbaa56 100644
--- a/docs/WindowsBuild.md
+++ b/docs/WindowsBuild.md
@@ -43,6 +43,12 @@
- Currently, other repositories in the Swift project have not been tested and
may not be supported.
+If your sources live else where, you can create a substitution for this:
+
+```cmd
+subst S: <path to sources>
+```
+
```cmd
git config --global core.autocrlf input
S:
@@ -60,21 +66,18 @@
1. Add the `bin64` folder to your `Path` environment variable.
### 4. Get ready
-- From within a **developer** command prompt (not PowerShell nor cmd, but [the
- Visual Studio Developer Command
- Prompt](https://msdn.microsoft.com/en-us/library/f35ctcxw.aspx)), execute the
- following command if you have an x64 PC.
+- From within a **developer** command prompt (not PowerShell nor cmd, but the [Visual Studio Developer Command Prompt](https://msdn.microsoft.com/en-us/library/f35ctcxw.aspx)), execute the following command if you have an x64 PC.
+
```cmd
VsDevCmd -arch=amd64
```
-If instead you're compiling for a 32-bit Windows target, adapt the `arch`
-argument to `x86` and run
+
+If instead you're compiling for a 32-bit Windows target, adapt the `arch` argument to `x86` and run
+
```cmd
VsDevCmd -arch=x86
```
-- We will use the assumption that the sources are on the `S` drive. Replace it with the path to the checkout. Make sure to use forward slashes (`/`) instead of backslashes (`\`) as the path separators. `clang` breaks with backslashed paths.
-
- Decide whether you want to build a release or debug version of Swift on Windows and
replace the `CMAKE_BUILD_TYPE` parameter in the build steps below with the correct value
(`Debug`, `RelWithDebInfoAssert` or `Release`) to avoid conflicts between the debug and
@@ -85,23 +88,25 @@
`${UniversalCRTSdkDir}/Include/${UCRTVersion}/ucrt` as `module.modulemap`, copying `visualc.modulemap` located at `swift/stdlib/public/Platform/visualc.modulemap` into `${VCToolsInstallDir}/include` as `module.modulemap`, and copying `winsdk.modulemap` located at `swift/stdlib/public/Platform/winsdk.modulemap` into `${UniversalCRTSdkDir}/Include/${UCRTVersion}/um` and setup the `visualc.apinotes` located at `swift/stdlib/public/Platform/visualc.apinotes` into `${VCToolsInstallDir}/include` as `visualc.apinotes`
```cmd
-cd %UniversalCRTSdkDir%\Include\%UCRTVersion%\ucrt
-mklink module.modulemap S:\swift\stdlib\public\Platform\ucrt.modulemap
-cd %VCToolsInstallDir%\include
-mklink module.modulemap S:\swift\stdlib\public\Platform\visualc.modulemap
-mklink visualc.apinotes S:\swift\stdlib\public\Platform\visualc.apinotes
-cd %UniversalCRTSdkDir\Include\%UCRTVersion%\um
-mklink module.modulemap S:\swift\stdlib\public\Platform\winsdk.modulemap
+mklink %UniversalCRTSdkDir%\Include\%UCRTVersion%\ucrt\module.modulemap S:\swift\stdlib\public\Platform\ucrt.modulemap
+mklink %VCToolsInstallDir%\include\module.modulemap S:\swift\stdlib\public\Platform\visualc.modulemap
+mklink %VCToolsInstallDir%\include\visualc.apinotes S:\swift\stdlib\public\Platform\visualc.apinotes
+mklink %UniversalCRTSdkDir%\Include\%UCRTVersion%\um\module.modulemap S:\swift\stdlib\public\Platform\winsdk.modulemap
```
### 5. Build CMark
- This must be done from within a developer command prompt. CMark is a fairly
small project and should only take a few minutes to build.
```cmd
-mkdir S:/build/Ninja-DebugAssert/cmark-windows-amd64"
-pushd S:/build/Ninja-DebugAssert/cmark-windows-amd64" "S:/%swift_source_dir%/cmark"
+mkdir S:\build\Ninja-DebugAssert\cmark-windows-amd64"
+pushd S:\build\Ninja-DebugAssert\cmark-windows-amd64" "S:\cmark"
+cmake -G Ninja^
+ -DCMAKE_BUILD_TYPE=Debug^
+ -DCMAKE_C_COMPILER=cl^
+ -DCMAKE_CXX_COMPIELR=cl^
+ S:\cmark
popd
-cmake --build "S:/build/Ninja-DebugAssert/cmark-windows-amd64/"
+cmake --build "S:\build\Ninja-DebugAssert\cmark-windows-amd64"
```
### 6. Build LLVM/Clang
@@ -110,20 +115,23 @@
type (e.g. `Debug`, `Release`, `RelWithDebInfoAssert`) for LLVM/Clang matches the
build type for Swift.
```cmd
-mkdir "S:/build/Ninja-DebugAssert/llvm-windows-amd64"
-pushd "S:/build/Ninja-DebugAssert/llvm-windows-amd64"
+mkdir "S:\build\Ninja-DebugAssert\llvm-windows-amd64"
+pushd "S:\build\Ninja-DebugAssert\llvm-windows-amd64"
cmake -G "Ninja"^
- -DLLVM_ENABLE_ASSERTIONS=TRUE^
-DCMAKE_BUILD_TYPE=Debug^
+ -DCMAKE_C_COMPILER=cl^
+ -DCMAKE_CXX_COMPILER=cl^
+ -DLLVM_DEFAULT_TARGET_TRIPLE=x86_64-unknown-windows-msvc^
+ -DLLVM_ENABLE_ASSERTIONS=TRUE^
-DLLVM_ENABLE_PROJECTS=clang^
-DLLVM_TARGETS_TO_BUILD=X86^
- -DLLVM_DEFAULT_TARGET_TRIPLE=x86_64-unknown-windows-msvc^
- "S:/llvm"
+ "S:\llvm"
popd
-cmake --build "S:/build/Ninja-DebugAssert/llvm-windows-amd64"
+cmake --build "S:\build\Ninja-DebugAssert\llvm-windows-amd64"
```
-- If you intend to build any libraries, update your path to include the LLVM tools.
+- Update your path to include the LLVM tools.
+
```cmd
set PATH=%PATH%;S:\build\Ninja-DebugAssert\llvm-windows-amd64\bin
```
@@ -134,31 +142,31 @@
- You may need to adjust the `SWIFT_WINDOWS_LIB_DIRECTORY` parameter depending on
your target platform or Windows SDK version.
```cmd
-mkdir "S:/build/Ninja-DebugAssert/swift-windows-amd64"
-pushd "S:/build/Ninja-DebugAssert/swift-windows-amd64"
+mkdir "S:\build\Ninja-DebugAssert\swift-windows-amd64"
+pushd "S:\build\inja-DebugAssert\swift-windows-amd64"
cmake -G "Ninja"^
-DCMAKE_BUILD_TYPE=Debug^
- -DCMAKE_C_COMPILER="S:/build/Ninja-DebugAssert/llvm-windows-amd64/clang-cl.exe"^
- -DCMAKE_CXX_COMPILER="S:/build/Ninja-DebugAssert/llvm-windows-amd64/clang-cl.exe"^
- -DSWIFT_PATH_TO_CMARK_SOURCE="S:/cmark"^
+ -DCMAKE_C_COMPILER=clang-cl^
+ -DCMAKE_CXX_COMPILER=clang-cl^
+ -DSWIFT_PATH_TO_CMARK_SOURCE="S:\cmark"^
-DCMAKE_CXX_FLAGS="-Wno-c++98-compat -Wno-c++98-compat-pedantic"^
-DCMAKE_EXE_LINKER_FLAGS:STRING="/INCREMENTAL:NO"^
-DCMAKE_SHARED_LINKER_FLAGS="/INCREMENTAL:NO"^
-DSWIFT_INCLUDE_DOCS=NO^
- -DSWIFT_PATH_TO_LLVM_SOURCE="S:/llvm"^
- -DSWIFT_PATH_TO_CLANG_SOURCE="S:/clang"^
- -DSWIFT_PATH_TO_LIBDISPATCH_SOURCE="S:/swift-corelibs-libdispatch"^
- -DSWIFT_PATH_TO_LLVM_BUILD="S:/build/Ninja-DebugAssert/llvm-windows-amd64"^
- -DSWIFT_PATH_TO_CLANG_BUILD="S:/build/Ninja-DebugAssert/llvm-windows-amd64"^
- -DSWIFT_PATH_TO_CMARK_BUILD="S:/build/Ninja-DebugAssert/cmark-windows-amd64"^
- -DSWIFT_WINDOWS_x86_64_ICU_UC_INCLUDE="S:/icu/include"^
- -DSWIFT_WINDOWS_x86_64_ICU_UC="S:/icu/lib64/icuuc.lib"^
- -DSWIFT_WINDOWS_x86_64_ICU_I18N_INCLUDE="S:/icu/include"^
- -DSWIFT_WINDOWS_x86_64_ICU_I18N="S:/icu/lib64/icuin.lib"^
- -DCMAKE_INSTALL_PREFIX="C:/Program Files (x86)/Swift"^
- "S:/swift"
+ -DSWIFT_PATH_TO_LLVM_SOURCE="S:\llvm"^
+ -DSWIFT_PATH_TO_CLANG_SOURCE="S:\clang"^
+ -DSWIFT_PATH_TO_LIBDISPATCH_SOURCE="S:\swift-corelibs-libdispatch"^
+ -DSWIFT_PATH_TO_LLVM_BUILD="S:\build\Ninja-DebugAssert\llvm-windows-amd64"^
+ -DSWIFT_PATH_TO_CLANG_BUILD="S:\build\Ninja-DebugAssert\llvm-windows-amd64"^
+ -DSWIFT_PATH_TO_CMARK_BUILD="S:\build\Ninja-DebugAssert\cmark-windows-amd64"^
+ -DSWIFT_WINDOWS_x86_64_ICU_UC_INCLUDE="S:\icu\include"^
+ -DSWIFT_WINDOWS_x86_64_ICU_UC="S:\icu\lib64\icuuc.lib"^
+ -DSWIFT_WINDOWS_x86_64_ICU_I18N_INCLUDE="S:\icu\include"^
+ -DSWIFT_WINDOWS_x86_64_ICU_I18N="S:\icu\lib64\icuin.lib"^
+ -DCMAKE_INSTALL_PREFIX="C:\Library\Developer\Toolchains\unknown-Asserts-development.xctoolchain\usr"^
+ "S:\swift"
popd
-cmake --build "S:/build/Ninja-DebugAssert/swift-windows-amd64"
+cmake --build "S:\build\Ninja-DebugAssert\swift-windows-amd64"
```
- To create a Visual Studio project, you'll need to change the generator and,
@@ -169,9 +177,7 @@
a file.
```cmd
-cmake -G "Visual Studio 2017" "%swift_source_dir%/swift"^
- -DCMAKE_GENERATOR_PLATFORM="x64"^
- ...
+cmake -G "Visual Studio 2017" "S:\swift" -DCMAKE_GENERATOR_PLATFORM="x64"^ ...
```
### 8. Build lldb
@@ -251,14 +257,13 @@
### 12. Install Swift on Windows
- Run ninja install:
+
```cmd
ninja -C "S:/build/Ninja-DebugAssert/swift-windows-amd64" install
```
-- Add the Swift on Windows binaries path (`C:\Program Files (x86)\Swift\bin`) to the
- `Path` environment variable.
-- Add the Swift on Windows library path (`C:\Program Files (x86)\Swift\lib\swift\windows`)
- to the `Path` environment variable.
+
+- Add the Swift on Windows binaries path (`C:\Library\Developer\Toolchains\unknown-Asserts-development.xctoolchain\usr\bin`) to the `PATH` environment variable.
## MSVC
-To use `cl` instead, just remove the `-DCMAKE_C_COMPILER` and `-DCMAKE_CXX_COMPILER` parameters to the `cmake` invocations.
+To use `cl` instead, just replace the `-DCMAKE_C_COMPILER` and `-DCMAKE_CXX_COMPILER` parameters to the `cmake` invocations.
diff --git a/include/swift/AST/AccessScope.h b/include/swift/AST/AccessScope.h
index b8a200f..a8e1444 100644
--- a/include/swift/AST/AccessScope.h
+++ b/include/swift/AST/AccessScope.h
@@ -47,6 +47,7 @@
bool isPublic() const { return !Value.getPointer(); }
bool isPrivate() const { return Value.getInt(); }
bool isFileScope() const;
+ bool isInternal() const;
/// Returns true if this is a child scope of the specified other access scope.
///
diff --git a/include/swift/AST/Builtins.def b/include/swift/AST/Builtins.def
index f88c975..4b0c973 100644
--- a/include/swift/AST/Builtins.def
+++ b/include/swift/AST/Builtins.def
@@ -423,9 +423,29 @@
BUILTIN_MISC_OPERATION(Alignof, "alignof", "n", Special)
/// AllocRaw has type (Int, Int) -> Builtin.RawPointer
+///
+/// Parameters: object size, object alignment.
+///
+/// This alignment is not a mask; the compiler decrements by one to provide
+/// a mask to the runtime.
+///
+/// If alignment == 0, then the runtime will use "aligned" allocation,
+/// and the memory will be aligned to _swift_MinAllocationAlignment.
BUILTIN_MISC_OPERATION(AllocRaw, "allocRaw", "", Special)
/// DeallocRaw has type (Builtin.RawPointer, Int, Int) -> ()
+///
+/// Parameters: object address, object size, object alignment.
+///
+/// This alignment is not a mask; the compiler decrements by one to provide
+/// a mask to the runtime.
+///
+/// If alignment == 0, then the runtime will use the "aligned" deallocation
+/// path, which assumes that "aligned" allocation was used.
+///
+/// Note that the alignment value provided to `deallocRaw` must be identical to
+/// the alignment value provided to `allocRaw` when the memory at this address
+/// was allocated.
BUILTIN_MISC_OPERATION(DeallocRaw, "deallocRaw", "", Special)
/// Fence has type () -> ().
diff --git a/include/swift/AST/SwiftNameTranslation.h b/include/swift/AST/SwiftNameTranslation.h
index fa9836a..1f07c28 100644
--- a/include/swift/AST/SwiftNameTranslation.h
+++ b/include/swift/AST/SwiftNameTranslation.h
@@ -18,6 +18,7 @@
namespace swift {
class ValueDecl;
+ class EnumDecl;
class EnumElementDecl;
namespace objc_translation {
@@ -29,6 +30,8 @@
StringRef getNameForObjC(const ValueDecl *VD,
CustomNamesOnly_t customNamesOnly = Normal);
+ std::string getErrorDomainStringForObjC(const EnumDecl *ED);
+
/// Print the ObjC name of an enum element decl to OS, also allowing the client
/// to specify a preferred name other than the decl's original name.
///
diff --git a/include/swift/Demangling/TypeDecoder.h b/include/swift/Demangling/TypeDecoder.h
index 55ed17d..0005bf7 100644
--- a/include/swift/Demangling/TypeDecoder.h
+++ b/include/swift/Demangling/TypeDecoder.h
@@ -163,9 +163,15 @@
case NodeKind::BoundGenericClass:
{
#if SWIFT_OBJC_INTEROP
- if (Node->getNumChildren() == 2)
- if (auto mangledName = getObjCClassOrProtocolName(Node->getChild(0)))
+ if (Node->getNumChildren() >= 2) {
+ auto ChildNode = Node->getChild(0);
+ if (ChildNode->getKind() == NodeKind::Type &&
+ ChildNode->getNumChildren() > 0)
+ ChildNode = ChildNode->getChild(0);
+
+ if (auto mangledName = getObjCClassOrProtocolName(ChildNode))
return Builder.createObjCClassType(mangledName->str());
+ }
#endif
LLVM_FALLTHROUGH;
}
diff --git a/lib/AST/ASTPrinter.cpp b/lib/AST/ASTPrinter.cpp
index 8177807..b28ed6c 100644
--- a/lib/AST/ASTPrinter.cpp
+++ b/lib/AST/ASTPrinter.cpp
@@ -889,8 +889,8 @@
if (auto vd = dyn_cast<VarDecl>(D)) {
// Don't print @_hasInitialValue if we're printing an initializer
- // expression.
- if (vd->isInitExposedToClients())
+ // expression or if the storage is resilient.
+ if (vd->isInitExposedToClients() || vd->isResilient())
Options.ExcludeAttrList.push_back(DAK_HasInitialValue);
if (!Options.PrintForSIL) {
diff --git a/lib/AST/DeclContext.cpp b/lib/AST/DeclContext.cpp
index a19869c..4694e95 100644
--- a/lib/AST/DeclContext.cpp
+++ b/lib/AST/DeclContext.cpp
@@ -839,6 +839,11 @@
return DC && isa<FileUnit>(DC);
}
+bool AccessScope::isInternal() const {
+ auto DC = getDeclContext();
+ return DC && isa<ModuleDecl>(DC);
+}
+
AccessLevel AccessScope::accessLevelForDiagnostics() const {
if (isPublic())
return AccessLevel::Public;
diff --git a/lib/AST/SwiftNameTranslation.cpp b/lib/AST/SwiftNameTranslation.cpp
index b7661c1..f928669 100644
--- a/lib/AST/SwiftNameTranslation.cpp
+++ b/lib/AST/SwiftNameTranslation.cpp
@@ -16,6 +16,7 @@
#include "swift/AST/SwiftNameTranslation.h"
#include "swift/AST/ASTContext.h"
+#include "swift/AST/Module.h"
#include "swift/AST/Decl.h"
#include "swift/AST/LazyResolver.h"
#include "swift/Basic/StringExtras.h"
@@ -51,6 +52,34 @@
return VD->getBaseName().getIdentifier().str();
}
+std::string swift::objc_translation::
+getErrorDomainStringForObjC(const EnumDecl *ED) {
+ // Should have already been diagnosed as diag::objc_enum_generic.
+ assert(!ED->isGenericContext() && "Trying to bridge generic enum error to Obj-C");
+
+ // Clang decls have custom domains, but we shouldn't see them here anyway.
+ assert(!ED->getClangDecl() && "clang decls shouldn't be re-exported");
+
+ SmallVector<const NominalTypeDecl *, 4> outerTypes;
+ for (const NominalTypeDecl * D = ED;
+ D != nullptr;
+ D = D->getDeclContext()->getSelfNominalTypeDecl()) {
+ // We don't currently PrintAsObjC any types whose parents are private or
+ // fileprivate.
+ assert(D->getFormalAccess() >= AccessLevel::Internal &&
+ "We don't currently append private discriminators");
+ outerTypes.push_back(D);
+ }
+
+ std::string buffer = ED->getParentModule()->getNameStr();
+ for (auto D : reversed(outerTypes)) {
+ buffer += ".";
+ buffer += D->getNameStr();
+ }
+
+ return buffer;
+}
+
bool swift::objc_translation::
printSwiftEnumElemNameInObjC(const EnumElementDecl *EL, llvm::raw_ostream &OS,
Identifier PreferredName) {
diff --git a/lib/ParseSIL/ParseSIL.cpp b/lib/ParseSIL/ParseSIL.cpp
index 43fe6b2..eff9aea 100644
--- a/lib/ParseSIL/ParseSIL.cpp
+++ b/lib/ParseSIL/ParseSIL.cpp
@@ -1399,21 +1399,24 @@
ParseState = 1;
} else if (!ParseState &&
(accessorKind = getAccessorKind(Id.str())).hasValue()) {
- auto storageDecl = dyn_cast<AbstractStorageDecl>(VD);
- auto accessor = (storageDecl
- ? storageDecl->getAccessor(*accessorKind)
- : nullptr);
- if (!accessor) {
+ // Drill down to the corresponding accessor for each declaration,
+ // compacting away decls that lack it.
+ size_t destI = 0;
+ for (size_t srcI = 0, e = values.size(); srcI != e; ++srcI) {
+ if (auto storage = dyn_cast<AbstractStorageDecl>(values[srcI]))
+ if (auto accessor = storage->getAccessor(*accessorKind))
+ values[destI++] = accessor;
+ }
+ values.resize(destI);
+
+ // Complain if none of the decls had a corresponding accessor.
+ if (destI == 0) {
P.diagnose(IdLoc, diag::referenced_value_no_accessor, 0);
return true;
}
+
Kind = SILDeclRef::Kind::Func;
- VD = accessor;
- // Update values for this accessor kind.
- for (unsigned I = 0, E = values.size(); I < E; I++)
- if (auto otherDecl = dyn_cast<AbstractStorageDecl>(values[I]))
- if (auto otherAccessor = otherDecl->getAccessor(*accessorKind))
- values[I] = otherAccessor;
+ VD = values[0];
ParseState = 1;
} else if (!ParseState && Id.str() == "allocator") {
Kind = SILDeclRef::Kind::Allocator;
diff --git a/lib/PrintAsObjC/PrintAsObjC.cpp b/lib/PrintAsObjC/PrintAsObjC.cpp
index 0a2e514..85434fe 100644
--- a/lib/PrintAsObjC/PrintAsObjC.cpp
+++ b/lib/PrintAsObjC/PrintAsObjC.cpp
@@ -2511,7 +2511,7 @@
});
if (!hasDomainCase) {
os << "static NSString * _Nonnull const " << getNameForObjC(ED)
- << "Domain = @\"" << M.getName() << "." << ED->getName() << "\";\n";
+ << "Domain = @\"" << getErrorDomainStringForObjC(ED) << "\";\n";
}
}
diff --git a/lib/Sema/DerivedConformanceError.cpp b/lib/Sema/DerivedConformanceError.cpp
index 9d25faf..6cb14e4 100644
--- a/lib/Sema/DerivedConformanceError.cpp
+++ b/lib/Sema/DerivedConformanceError.cpp
@@ -22,11 +22,40 @@
#include "swift/AST/Expr.h"
#include "swift/AST/Module.h"
#include "swift/AST/Types.h"
+#include "swift/AST/SwiftNameTranslation.h"
using namespace swift;
+using namespace swift::objc_translation;
static void deriveBodyBridgedNSError_enum_nsErrorDomain(
- AbstractFunctionDecl *domainDecl, void *) {
+ AbstractFunctionDecl *domainDecl, void *) {
+ // enum SomeEnum {
+ // @derived
+ // static var _nsErrorDomain: String {
+ // return String(reflecting: self)
+ // }
+ // }
+
+ auto M = domainDecl->getParentModule();
+ auto &C = M->getASTContext();
+ auto self = domainDecl->getImplicitSelfDecl();
+
+ auto selfRef = new (C) DeclRefExpr(self, DeclNameLoc(), /*implicit*/ true);
+ auto stringType = TypeExpr::createForDecl(SourceLoc(), C.getStringDecl(),
+ domainDecl, /*implicit*/ true);
+ auto initReflectingCall =
+ CallExpr::createImplicit(C, stringType,
+ { selfRef }, { C.getIdentifier("reflecting") });
+ auto ret =
+ new (C) ReturnStmt(SourceLoc(), initReflectingCall, /*implicit*/ true);
+
+ auto body = BraceStmt::create(C, SourceLoc(), ASTNode(ret), SourceLoc());
+
+ domainDecl->setBody(body);
+}
+
+static void deriveBodyBridgedNSError_printAsObjCEnum_nsErrorDomain(
+ AbstractFunctionDecl *domainDecl, void *) {
// enum SomeEnum {
// @derived
// static var _nsErrorDomain: String {
@@ -39,10 +68,7 @@
auto TC = domainDecl->getInnermostTypeContext();
auto ED = TC->getSelfEnumDecl();
- std::string buffer = M->getNameStr();
- buffer += ".";
- buffer += ED->getNameStr();
- StringRef value(C.AllocateCopy(buffer));
+ StringRef value(C.AllocateCopy(getErrorDomainStringForObjC(ED)));
auto string = new (C) StringLiteralExpr(value, SourceRange(), /*implicit*/ true);
auto ret = new (C) ReturnStmt(SourceLoc(), string, /*implicit*/ true);
@@ -53,17 +79,15 @@
}
static ValueDecl *
-deriveBridgedNSError_enum_nsErrorDomain(DerivedConformance &derived) {
+deriveBridgedNSError_enum_nsErrorDomain(DerivedConformance &derived,
+ void (*synthesizer)(AbstractFunctionDecl *, void*)) {
// enum SomeEnum {
// @derived
// static var _nsErrorDomain: String {
- // return "\(self)"
+ // ...
// }
// }
- // Note that for @objc enums the format is assumed to be "MyModule.SomeEnum".
- // If this changes, please change PrintAsObjC as well.
-
ASTContext &C = derived.TC.Context;
auto stringTy = C.getStringDecl()->getDeclaredType();
@@ -78,7 +102,7 @@
// Define the getter.
auto getterDecl = derived.addGetterToReadOnlyDerivedProperty(
derived.TC, propDecl, stringTy);
- getterDecl->setBodySynthesizer(&deriveBodyBridgedNSError_enum_nsErrorDomain);
+ getterDecl->setBodySynthesizer(synthesizer);
derived.addMembersToConformanceContext({getterDecl, propDecl, pbDecl});
@@ -89,8 +113,17 @@
if (!isa<EnumDecl>(Nominal))
return nullptr;
- if (requirement->getBaseName() == TC.Context.Id_nsErrorDomain)
- return deriveBridgedNSError_enum_nsErrorDomain(*this);
+ if (requirement->getBaseName() == TC.Context.Id_nsErrorDomain) {
+ auto synthesizer = deriveBodyBridgedNSError_enum_nsErrorDomain;
+
+ auto scope = Nominal->getFormalAccessScope(Nominal->getModuleScopeContext());
+ if (scope.isPublic() || scope.isInternal())
+ // PrintAsObjC may print this domain, so we should make sure we use the
+ // same string it will.
+ synthesizer = deriveBodyBridgedNSError_printAsObjCEnum_nsErrorDomain;
+
+ return deriveBridgedNSError_enum_nsErrorDomain(*this, synthesizer);
+ }
TC.diagnose(requirement->getLoc(), diag::broken_errortype_requirement);
return nullptr;
diff --git a/stdlib/private/StdlibUnittest/CMakeLists.txt b/stdlib/private/StdlibUnittest/CMakeLists.txt
index c57d075..ffac1c3 100644
--- a/stdlib/private/StdlibUnittest/CMakeLists.txt
+++ b/stdlib/private/StdlibUnittest/CMakeLists.txt
@@ -10,8 +10,6 @@
list(APPEND swift_stdlib_unittest_compile_flags "-DSWIFT_STDLIB_DEBUG")
endif()
-# TODO: support this on non-POSIX platforms. It cannot be currently as it
-# depends on pthreads.
add_swift_target_library(swiftStdlibUnittest ${SWIFT_STDLIB_LIBRARY_BUILD_TYPES} IS_STDLIB
# This file should be listed the first. Module name is inferred from the
# filename.
@@ -42,7 +40,8 @@
SWIFT_MODULE_DEPENDS_FREEBSD Glibc
SWIFT_MODULE_DEPENDS_CYGWIN Glibc
SWIFT_MODULE_DEPENDS_HAIKU Glibc
+ SWIFT_MODULE_DEPENDS_WINDOWS MSVCRT WinSDK
SWIFT_COMPILE_FLAGS ${swift_stdlib_unittest_compile_flags}
- TARGET_SDKS ALL_POSIX_PLATFORMS
INSTALL_IN_COMPONENT stdlib-experimental)
+set_source_files_properties(InspectValue.cpp PROPERTIES COMPILE_FLAGS -std=c++14)
diff --git a/stdlib/private/StdlibUnittest/InterceptTraps.cpp b/stdlib/private/StdlibUnittest/InterceptTraps.cpp
index e8f7987..377397b 100644
--- a/stdlib/private/StdlibUnittest/InterceptTraps.cpp
+++ b/stdlib/private/StdlibUnittest/InterceptTraps.cpp
@@ -13,7 +13,16 @@
#include <stdio.h>
#include <signal.h>
#include <string.h>
+#if defined(__unix__) || (defined(__APPLE__) && defined(__MACH__))
#include <unistd.h>
+#endif
+#if defined(_WIN32)
+#include <io.h>
+#include <process.h>
+#include <stdlib.h>
+#define WIN32_LEAN_AND_MEAN
+#include <Windows.h>
+#endif
#include "swift/Runtime/Config.h"
@@ -21,29 +30,60 @@
const char *Msg;
switch (Sig) {
case SIGILL: Msg = "CRASHED: SIGILL\n"; break;
- case SIGTRAP: Msg = "CRASHED: SIGTRAP\n"; break;
case SIGABRT: Msg = "CRASHED: SIGABRT\n"; break;
case SIGFPE: Msg = "CRASHED: SIGFPE\n"; break;
- case SIGBUS: Msg = "CRASHED: SIGBUS\n"; break;
case SIGSEGV: Msg = "CRASHED: SIGSEGV\n"; break;
+#if !defined(_WIN32)
+ case SIGTRAP: Msg = "CRASHED: SIGTRAP\n"; break;
+ case SIGBUS: Msg = "CRASHED: SIGBUS\n"; break;
case SIGSYS: Msg = "CRASHED: SIGSYS\n"; break;
+#endif
default: Msg = "CRASHED: SIG????\n"; break;
}
+#if defined(_WIN32)
+ _write(_fileno(stderr), Msg, strlen(Msg));
+#else
write(STDERR_FILENO, Msg, strlen(Msg));
+#endif
_exit(0);
}
+#if defined(_WIN32)
+static LONG WINAPI
+VectoredCrashHandler(PEXCEPTION_POINTERS ExceptionInfo) {
+ switch (ExceptionInfo->ExceptionRecord->ExceptionCode) {
+ case EXCEPTION_ILLEGAL_INSTRUCTION:
+ _write(_fileno(stderr), "CRASHED: SIGTRAP\n", 17);
+ _exit(0);
+
+ case EXCEPTION_DATATYPE_MISALIGNMENT:
+ _write(_fileno(stderr), "CRASHED: SIGBUS\n", 16);
+ _exit(0);
+ }
+
+ return EXCEPTION_CONTINUE_SEARCH;
+}
+#endif
+
SWIFT_CC(swift) SWIFT_RUNTIME_LIBRARY_VISIBILITY extern "C"
void installTrapInterceptor() {
// Disable buffering on stdout so that everything is printed before crashing.
setbuf(stdout, 0);
+#if defined(_WIN32)
+ _set_abort_behavior(0, _WRITE_ABORT_MSG);
+#endif
+
signal(SIGILL, CrashCatcher);
- signal(SIGTRAP, CrashCatcher);
signal(SIGABRT, CrashCatcher);
signal(SIGFPE, CrashCatcher);
- signal(SIGBUS, CrashCatcher);
signal(SIGSEGV, CrashCatcher);
+#if defined(_WIN32)
+ AddVectoredExceptionHandler(TRUE, VectoredCrashHandler);
+#else
+ signal(SIGTRAP, CrashCatcher);
+ signal(SIGBUS, CrashCatcher);
signal(SIGSYS, CrashCatcher);
+#endif
}
diff --git a/stdlib/private/StdlibUnittest/OpaqueIdentityFunctions.swift b/stdlib/private/StdlibUnittest/OpaqueIdentityFunctions.swift
index b3ec509..d4202a7 100644
--- a/stdlib/private/StdlibUnittest/OpaqueIdentityFunctions.swift
+++ b/stdlib/private/StdlibUnittest/OpaqueIdentityFunctions.swift
@@ -71,7 +71,7 @@
@inline(never)
public func getFloat64(_ x: Float64) -> Float64 { return _opaqueIdentity(x) }
-#if arch(i386) || arch(x86_64)
+#if !os(Windows) && (arch(i386) || arch(x86_64))
@inline(never)
public func getFloat80(_ x: Float80) -> Float80 { return _opaqueIdentity(x) }
#endif
diff --git a/stdlib/private/StdlibUnittest/RaceTest.swift b/stdlib/private/StdlibUnittest/RaceTest.swift
index a36e706..1db9947 100644
--- a/stdlib/private/StdlibUnittest/RaceTest.swift
+++ b/stdlib/private/StdlibUnittest/RaceTest.swift
@@ -43,6 +43,9 @@
import Darwin
#elseif os(Linux) || os(FreeBSD) || os(PS4) || os(Android) || os(Cygwin) || os(Haiku)
import Glibc
+#elseif os(Windows)
+import MSVCRT
+import WinSDK
#endif
#if _runtime(_ObjC)
@@ -508,6 +511,36 @@
}
/// One-shot sleep in one thread, allowing interrupt by another.
+#if os(Windows)
+class _InterruptibleSleep {
+ let event: HANDLE?
+ var completed: Bool = false
+
+ init() {
+ self.event = CreateEventW(nil, TRUE, FALSE, nil)
+ precondition(self.event != nil)
+ }
+
+ deinit {
+ CloseHandle(self.event)
+ }
+
+ func sleep(durationInSeconds duration: Int) {
+ guard completed == false else { return }
+
+ let result: DWORD = WaitForSingleObject(event, DWORD(duration * 1000))
+ precondition(result == WAIT_OBJECT_0)
+
+ completed = true
+ }
+
+ func wake() {
+ guard completed == false else { return }
+ let result: BOOL = SetEvent(self.event)
+ precondition(result == TRUE)
+ }
+}
+#else
class _InterruptibleSleep {
let writeEnd: CInt
let readEnd: CInt
@@ -550,6 +583,13 @@
precondition(ret >= 0)
}
}
+#endif
+
+#if os(Windows)
+typealias ThreadHandle = HANDLE
+#else
+typealias ThreadHandle = pthread_t
+#endif
public func runRaceTest<RT : RaceTestWithPerTrialData>(
_: RT.Type,
@@ -600,8 +640,8 @@
_ = timeoutReached.fetchAndAdd(1)
}
- var testTids = [pthread_t]()
- var alarmTid: pthread_t
+ var testTids = [ThreadHandle]()
+ var alarmTid: ThreadHandle
// Create the master thread.
do {
diff --git a/stdlib/private/StdlibUnittest/StdlibCoreExtras.swift b/stdlib/private/StdlibUnittest/StdlibCoreExtras.swift
index 5159289..6d9260e 100644
--- a/stdlib/private/StdlibUnittest/StdlibCoreExtras.swift
+++ b/stdlib/private/StdlibUnittest/StdlibCoreExtras.swift
@@ -16,6 +16,8 @@
import Darwin
#elseif os(Linux) || os(FreeBSD) || os(PS4) || os(Android) || os(Cygwin) || os(Haiku)
import Glibc
+#elseif os(Windows)
+import MSVCRT
#endif
#if _runtime(_ObjC)
@@ -73,6 +75,7 @@
#endif
}
+#if !os(Windows)
public func createTemporaryFile(
_ fileNamePrefix: String, _ fileNameSuffix: String, _ contents: String
) -> String {
@@ -95,6 +98,7 @@
}
return fileName
}
+#endif
public final class Box<T> {
public init(_ value: T) { self.value = value }
diff --git a/stdlib/private/StdlibUnittest/StdlibUnittest.swift b/stdlib/private/StdlibUnittest/StdlibUnittest.swift
index c28affd..f7e1d9a 100644
--- a/stdlib/private/StdlibUnittest/StdlibUnittest.swift
+++ b/stdlib/private/StdlibUnittest/StdlibUnittest.swift
@@ -19,6 +19,9 @@
import Darwin
#elseif os(Linux) || os(FreeBSD) || os(PS4) || os(Android) || os(Cygwin) || os(Haiku)
import Glibc
+#elseif os(Windows)
+import MSVCRT
+import WinSDK
#endif
#if _runtime(_ObjC)
@@ -718,7 +721,11 @@
var isSwiftTrap: Bool {
switch self {
case .signal(let signal):
+#if os(Windows)
+ return CInt(signal) == SIGILL
+#else
return CInt(signal) == SIGILL || CInt(signal) == SIGTRAP
+#endif
default:
// This default case is needed for standard library builds where
// resilience is enabled.
@@ -749,12 +756,21 @@
func _printDebuggingAdvice(_ fullTestName: String) {
print("To debug, run:")
var invocation = [CommandLine.arguments[0]]
+#if os(Windows)
+ var buffer: UnsafeMutablePointer<CChar>?
+ var length: Int = 0
+ if _dupenv_s(&buffer, &length, "SWIFT_INTERPRETER") != 0, let buffer = buffer {
+ invocation.insert(String(cString: buffer), at: 0)
+ free(buffer)
+ }
+#else
let interpreter = getenv("SWIFT_INTERPRETER")
if interpreter != nil {
if let interpreterCmd = String(validatingUTF8: interpreter!) {
invocation.insert(interpreterCmd, at: 0)
}
}
+#endif
print("$ \(invocation.joined(separator: " ")) " +
"--stdlib-unittest-in-process --stdlib-unittest-filter \"\(fullTestName)\"")
}
@@ -829,11 +845,21 @@
}
}
-struct _ParentProcess {
+class _ParentProcess {
+#if os(Windows)
+ internal var _process: HANDLE = INVALID_HANDLE_VALUE
+ internal var _childStdin: _FDOutputStream =
+ _FDOutputStream(handle: INVALID_HANDLE_VALUE)
+ internal var _childStdout: _FDInputStream =
+ _FDInputStream(handle: INVALID_HANDLE_VALUE)
+ internal var _childStderr: _FDInputStream =
+ _FDInputStream(handle: INVALID_HANDLE_VALUE)
+#else
internal var _pid: pid_t?
internal var _childStdin: _FDOutputStream = _FDOutputStream(fd: -1)
internal var _childStdout: _FDInputStream = _FDInputStream(fd: -1)
internal var _childStderr: _FDInputStream = _FDInputStream(fd: -1)
+#endif
internal var _runTestsInProcess: Bool
internal var _filter: String?
@@ -845,16 +871,32 @@
self._args = args
}
- mutating func _spawnChild() {
+ func _spawnChild() {
let params = ["--stdlib-unittest-run-child"] + _args
+#if os(Windows)
+ let (hProcess, hStdIn, hStdOut, hStdErr) = spawnChild(params)
+ self._process = hProcess
+ self._childStdin = _FDOutputStream(handle: hStdIn)
+ self._childStdout = _FDInputStream(handle: hStdOut)
+ self._childStderr = _FDInputStream(handle: hStdErr)
+#else
let (pid, childStdinFD, childStdoutFD, childStderrFD) = spawnChild(params)
_pid = pid
_childStdin = _FDOutputStream(fd: childStdinFD)
_childStdout = _FDInputStream(fd: childStdoutFD)
_childStderr = _FDInputStream(fd: childStderrFD)
+#endif
}
- mutating func _waitForChild() -> ProcessTerminationStatus {
+ func _waitForChild() -> ProcessTerminationStatus {
+#if os(Windows)
+ let status = waitProcess(_process)
+ _process = INVALID_HANDLE_VALUE
+
+ _childStdin.close()
+ _childStdout.close()
+ _childStderr.close()
+#else
let status = posixWaitpid(_pid!)
_pid = nil
_childStdin.close()
@@ -863,13 +905,40 @@
_childStdin = _FDOutputStream(fd: -1)
_childStdout = _FDInputStream(fd: -1)
_childStderr = _FDInputStream(fd: -1)
+#endif
return status
}
- internal mutating func _readFromChild(
- onStdoutLine: (String) -> (done: Bool, Void),
- onStderrLine: (String) -> (done: Bool, Void)
+ internal func _readFromChild(
+ onStdoutLine: @escaping (String) -> (done: Bool, Void),
+ onStderrLine: @escaping (String) -> (done: Bool, Void)
) {
+#if os(Windows)
+ let (_, stdoutThread) = _stdlib_thread_create_block({
+ while !self._childStdout.isEOF {
+ self._childStdout.read()
+ while let line = self._childStdout.getline() {
+ var done: Bool
+ (done: done, ()) = onStdoutLine(line)
+ if done { return }
+ }
+ }
+ }, ())
+
+ let (_, stderrThread) = _stdlib_thread_create_block({
+ while !self._childStderr.isEOF {
+ self._childStderr.read()
+ while let line = self._childStderr.getline() {
+ var done: Bool
+ (done: done, ()) = onStderrLine(line)
+ if done { return }
+ }
+ }
+ }, ())
+
+ let (_, _) = _stdlib_thread_join(stdoutThread!, Void.self)
+ let (_, _) = _stdlib_thread_join(stderrThread!, Void.self)
+#else
var readfds = _stdlib_fd_set()
var writefds = _stdlib_fd_set()
var errorfds = _stdlib_fd_set()
@@ -907,19 +976,26 @@
continue
}
}
+#endif
}
/// Returns the values of the corresponding variables in the child process.
- internal mutating func _runTestInChild(
+ internal func _runTestInChild(
_ testSuite: TestSuite,
_ testName: String,
parameter: Int?
) -> (anyExpectFailed: Bool, seenExpectCrash: Bool,
status: ProcessTerminationStatus?,
crashStdout: [Substring], crashStderr: [Substring]) {
+#if os(Windows)
+ if _process == INVALID_HANDLE_VALUE {
+ _spawnChild()
+ }
+#else
if _pid == nil {
_spawnChild()
}
+#endif
print("\(testSuite.name);\(testName)", terminator: "", to: &_childStdin)
if let parameter = parameter {
@@ -953,6 +1029,8 @@
omittingEmptySubsequences: false)
switch controlMessage[1] {
case "expectCrash":
+ fallthrough
+ case "expectCrash\r":
if isStdout {
stdoutSeenCrashDelimiter = true
anyExpectFailedInChild = controlMessage[2] == "true"
@@ -961,6 +1039,8 @@
expectingPreCrashMessage = String(controlMessage[2])
}
case "end":
+ fallthrough
+ case "end\r":
if isStdout {
stdoutEnd = true
anyExpectFailedInChild = controlMessage[2] == "true"
@@ -972,7 +1052,11 @@
}
line = line[line.startIndex..<index]
if line.isEmpty {
+#if os(Windows)
+ return (done: isStdout ? stdoutEnd : stderrEnd, ())
+#else
return (done: stdoutEnd && stderrEnd, ())
+#endif
}
}
if !expectingPreCrashMessage.isEmpty
@@ -1006,7 +1090,11 @@
} else {
print("stderr>>> \(line)")
}
+#if os(Windows)
+ return (done: isStdout ? stdoutEnd : stderrEnd, ())
+#else
return (done: stdoutEnd && stderrEnd, ())
+#endif
}
_readFromChild(
@@ -1042,12 +1130,20 @@
status, capturedCrashStdout, capturedCrashStderr)
}
- internal mutating func _shutdownChild() -> (failed: Bool, Void) {
+ internal func _shutdownChild() -> (failed: Bool, Void) {
+#if os(Windows)
+ if _process == INVALID_HANDLE_VALUE {
+ // The child process is not running. Report that it didn't fail during
+ // shutdown.
+ return (failed: false, ())
+ }
+#else
if _pid == nil {
// The child process is not running. Report that it didn't fail during
// shutdown.
return (failed: false, ())
}
+#endif
print("\(_stdlibUnittestStreamPrefix);shutdown", to: &_childStdin)
var childCrashed = false
@@ -1086,7 +1182,7 @@
case xFail
}
- internal mutating func runOneTest(
+ internal func runOneTest(
fullTestName: String,
testSuite: TestSuite,
test t: TestSuite._Test,
@@ -1172,7 +1268,7 @@
}
}
- mutating func run() {
+ func run() {
if let filter = _filter {
print("StdlibUnittest: using filter: \(filter)")
}
@@ -1347,7 +1443,7 @@
i += 1
}
- var parent = _ParentProcess(
+ let parent = _ParentProcess(
runTestsInProcess: runTestsInProcess, args: args, filter: filter)
parent.run()
}
diff --git a/stdlib/public/Platform/winsdk.modulemap b/stdlib/public/Platform/winsdk.modulemap
index e4d925b..89b6268 100644
--- a/stdlib/public/Platform/winsdk.modulemap
+++ b/stdlib/public/Platform/winsdk.modulemap
@@ -30,6 +30,12 @@
export *
}
+ // api-ms-win-heapapi-l1-1-0.dll
+ module heap {
+ header "heapapi.h"
+ export *
+ }
+
// api-ms-win-core-interlocked-l1-1-0.dll
module interlocked {
header "interlockedapi.h"
diff --git a/stdlib/public/SwiftShims/RuntimeShims.h b/stdlib/public/SwiftShims/RuntimeShims.h
index e108947..dc31840 100644
--- a/stdlib/public/SwiftShims/RuntimeShims.h
+++ b/stdlib/public/SwiftShims/RuntimeShims.h
@@ -56,6 +56,26 @@
SWIFT_RUNTIME_STDLIB_API
__swift_size_t _swift_stdlib_getHardwareConcurrency();
+/// Manually allocated memory is at least 16-byte aligned in Swift.
+///
+/// When swift_slowAlloc is called with "default" alignment (alignMask ==
+/// ~(size_t(0))), it will execute the "aligned allocation path" (AlignedAlloc)
+/// using this value for the alignment.
+///
+/// This is done so users do not need to specify the allocation alignment when
+/// manually deallocating memory via Unsafe[Raw][Buffer]Pointer. Any
+/// user-specified alignment less than or equal to _swift_MinAllocationAlignment
+/// results in a runtime request for "default" alignment. This guarantees that
+/// manual allocation always uses an "aligned" runtime allocation. If an
+/// allocation is "aligned" then it must be freed using an "aligned"
+/// deallocation. The converse must also hold. Since manual Unsafe*Pointer
+/// deallocation is always "aligned", the user never needs to specify alignment
+/// during deallocation.
+///
+/// This value is inlined (and constant propagated) in user code. On Windows,
+/// the Swift runtime and user binaries need to agree on this value.
+#define _swift_MinAllocationAlignment (__swift_size_t) 16
+
#ifdef __cplusplus
}} // extern "C", namespace swift
#endif
diff --git a/stdlib/public/core/Builtin.swift b/stdlib/public/core/Builtin.swift
index f5f8fda..761df17 100644
--- a/stdlib/public/core/Builtin.swift
+++ b/stdlib/public/core/Builtin.swift
@@ -242,8 +242,6 @@
return Builtin.castReference(x)
}
-import SwiftShims
-
@inlinable
@inline(__always)
public func _getUnsafePointerToStoredProperties(_ x: AnyObject)
@@ -255,6 +253,18 @@
storedPropertyOffset
}
+/// Get the minimum alignment for manually allocated memory.
+///
+/// Memory allocated via UnsafeMutable[Raw][Buffer]Pointer must never pass
+/// an alignment less than this value to Builtin.allocRaw. This
+/// ensures that the memory can be deallocated without specifying the
+/// alignment.
+@inlinable
+@inline(__always)
+internal func _minAllocationAlignment() -> Int {
+ return _swift_MinAllocationAlignment
+}
+
//===----------------------------------------------------------------------===//
// Branch hints
//===----------------------------------------------------------------------===//
diff --git a/stdlib/public/core/CharacterProperties.swift b/stdlib/public/core/CharacterProperties.swift
index 4e1c0c5..0232d11 100644
--- a/stdlib/public/core/CharacterProperties.swift
+++ b/stdlib/public/core/CharacterProperties.swift
@@ -22,15 +22,31 @@
) == self.unicodeScalars.endIndex
}
- /// Whether this Character is ASCII.
+ /// A Boolean value indicating whether this is an ASCII character.
@inlinable
public var isASCII: Bool {
return asciiValue != nil
}
- /// Returns the ASCII encoding value of this Character, if ASCII.
+ /// The ASCII encoding value of this character, if it is an ASCII character.
///
- /// Note: "\r\n" (CR-LF) is normalized to "\n" (LF), which will return 0x0A
+ /// let chars: [Character] = ["a", " ", "™"]
+ /// for ch in chars {
+ /// print(ch, "-->", ch.properties.numericValue)
+ /// }
+ /// // a --> 97
+ /// // --> 32
+ /// // ™ --> nil
+ ///
+ /// A character with the value "\r\n" (CR-LF) is normalized to "\n" (LF) and
+ /// has an `asciiValue` property equal to 10.
+ ///
+ /// let cr = "\r" as Character
+ /// // cr.asciiValue == 13
+ /// let lf = "\n" as Character
+ /// // lf.asciiValue == 10
+ /// let crlf = "\r\n" as Character
+ /// // crlf.asciiValue == 10
@inlinable
public var asciiValue: UInt8? {
if _slowPath(self == "\r\n") { return 0x000A /* LINE FEED (LF) */ }
@@ -38,30 +54,31 @@
return UInt8(_firstScalar.value)
}
- /// Whether this Character represents whitespace, including newlines.
+ /// A Boolean value indicating whether this character represents whitespace,
+ /// including newlines.
///
- /// Examples:
- /// * "\t" (U+0009 CHARACTER TABULATION)
- /// * " " (U+0020 SPACE)
- /// * U+2029 PARAGRAPH SEPARATOR
- /// * U+3000 IDEOGRAPHIC SPACE
+ /// For example, the following characters all represent whitespace:
///
+ /// - "\t" (U+0009 CHARACTER TABULATION)
+ /// - " " (U+0020 SPACE)
+ /// - U+2029 PARAGRAPH SEPARATOR
+ /// - U+3000 IDEOGRAPHIC SPACE
public var isWhitespace: Bool {
return _firstScalar.properties.isWhitespace
}
- /// Whether this Character represents a newline.
+ /// A Boolean value indicating whether this character represents a newline.
///
- /// Examples:
- /// * "\n" (U+000A): LINE FEED (LF)
- /// * U+000B: LINE TABULATION (VT)
- /// * U+000C: FORM FEED (FF)
- /// * "\r" (U+000D): CARRIAGE RETURN (CR)
- /// * "\r\n" (U+000A U+000D): CR-LF
- /// * U+0085: NEXT LINE (NEL)
- /// * U+2028: LINE SEPARATOR
- /// * U+2029: PARAGRAPH SEPARATOR
+ /// For example, the following characters all represent newlines:
///
+ /// - "\n" (U+000A): LINE FEED (LF)
+ /// - U+000B: LINE TABULATION (VT)
+ /// - U+000C: FORM FEED (FF)
+ /// - "\r" (U+000D): CARRIAGE RETURN (CR)
+ /// - "\r\n" (U+000D U+000A): CR-LF
+ /// - U+0085: NEXT LINE (NEL)
+ /// - U+2028: LINE SEPARATOR
+ /// - U+2029: PARAGRAPH SEPARATOR
@inlinable
public var isNewline: Bool {
switch _firstScalar.value {
@@ -73,54 +90,78 @@
}
}
- /// Whether this Character represents a number.
+ /// A Boolean value indicating whether this character represents a number.
///
- /// Examples:
- /// * "7" (U+0037 DIGIT SEVEN)
- /// * "⅚" (U+215A VULGAR FRACTION FIVE SIXTHS)
- /// * "㊈" (U+3288 CIRCLED IDEOGRAPH NINE)
- /// * "𝟠" (U+1D7E0 MATHEMATICAL DOUBLE-STRUCK DIGIT EIGHT)
- /// * "๒" (U+0E52 THAI DIGIT TWO)
+ /// For example, the following characters all represent numbers:
///
+ /// - "7" (U+0037 DIGIT SEVEN)
+ /// - "⅚" (U+215A VULGAR FRACTION FIVE SIXTHS)
+ /// - "㊈" (U+3288 CIRCLED IDEOGRAPH NINE)
+ /// - "𝟠" (U+1D7E0 MATHEMATICAL DOUBLE-STRUCK DIGIT EIGHT)
+ /// - "๒" (U+0E52 THAI DIGIT TWO)
public var isNumber: Bool {
return _firstScalar.properties.numericType != nil
}
- /// Whether this Character represents a whole number. See
- /// `Character.wholeNumberValue`
+ /// A Boolean value indicating whether this character represents a whole
+ /// number.
+ ///
+ /// For example, the following characters all represent whole numbers:
+ ///
+ /// - "1" (U+0031 DIGIT ONE) => 1
+ /// - "५" (U+096B DEVANAGARI DIGIT FIVE) => 5
+ /// - "๙" (U+0E59 THAI DIGIT NINE) => 9
+ /// - "万" (U+4E07 CJK UNIFIED IDEOGRAPH-4E07) => 10_000
@inlinable
public var isWholeNumber: Bool {
return wholeNumberValue != nil
}
- /// If this Character is a whole number, return the value it represents, else
- /// nil.
+ /// The numeric value this character represents, if it represents a whole
+ /// number.
///
- /// Examples:
- /// * "1" (U+0031 DIGIT ONE) => 1
- /// * "५" (U+096B DEVANAGARI DIGIT FIVE) => 5
- /// * "๙" (U+0E59 THAI DIGIT NINE) => 9
- /// * "万" (U+4E07 CJK UNIFIED IDEOGRAPH-4E07) => 10_000
+ /// If this character does not represent a whole number, or the value is too
+ /// large to represent as an `Int`, the value of this property is `nil`.
///
- /// Note: Returns nil on 32-bit platforms if the result would overflow `Int`.
+ /// let chars: [Character] = ["4", "④", "万", "a"]
+ /// for ch in chars {
+ /// print(ch, "-->", ch.properties.numericValue)
+ /// }
+ /// // 4 --> 4
+ /// // ④ --> 4
+ /// // 万 --> 10000
+ /// // a --> nil
public var wholeNumberValue: Int? {
guard _isSingleScalar else { return nil }
guard let value = _firstScalar.properties.numericValue else { return nil }
return Int(exactly: value)
}
- /// Whether this Character represents a hexadecimal digit.
+ /// A Boolean value indicating whether this character represents a
+ /// hexadecimal digit.
///
/// Hexadecimal digits include 0-9, Latin letters a-f and A-F, and their
- /// fullwidth compatibility forms. To get their value, see
- /// `Character.hexDigitValue`
+ /// fullwidth compatibility forms. To get the character's value, use the
+ /// `hexDigitValue` property.
@inlinable
public var isHexDigit: Bool {
return hexDigitValue != nil
}
- /// If this Character is a hexadecimal digit, returns the value it represents,
- /// else nil.
+ /// The numeric value this character represents, if it is a hexadecimal digit.
+ ///
+ /// Hexadecimal digits include 0-9, Latin letters a-f and A-F, and their
+ /// fullwidth compatibility forms. If the character does not represent a
+ /// hexadecimal digit, the value of this property is `nil`.
+ ///
+ /// let chars: [Character] = ["1", "a", "F", "g"]
+ /// for ch in chars {
+ /// print(ch, "-->", ch.hexDigitValue)
+ /// }
+ /// // 1 --> 1
+ /// // a --> 10
+ /// // F --> 15
+ /// // g --> nil
public var hexDigitValue: Int? {
guard _isSingleScalar else { return nil }
let value = _firstScalar.value
@@ -142,48 +183,51 @@
}
}
- /// Whether this Character is a letter.
+ /// A Boolean value indicating whether this character is a letter.
///
- /// Examples:
- /// * "A" (U+0041 LATIN CAPITAL LETTER A)
- /// * "é" (U+0065 LATIN SMALL LETTER E, U+0301 COMBINING ACUTE ACCENT)
- /// * "ϴ" (U+03F4 GREEK CAPITAL THETA SYMBOL)
- /// * "ڈ" (U+0688 ARABIC LETTER DDAL)
- /// * "日" (U+65E5 CJK UNIFIED IDEOGRAPH-65E5)
- /// * "ᚨ" (U+16A8 RUNIC LETTER ANSUZ A)
+ /// For example, the following characters are all letters:
///
+ /// - "A" (U+0041 LATIN CAPITAL LETTER A)
+ /// - "é" (U+0065 LATIN SMALL LETTER E, U+0301 COMBINING ACUTE ACCENT)
+ /// - "ϴ" (U+03F4 GREEK CAPITAL THETA SYMBOL)
+ /// - "ڈ" (U+0688 ARABIC LETTER DDAL)
+ /// - "日" (U+65E5 CJK UNIFIED IDEOGRAPH-65E5)
+ /// - "ᚨ" (U+16A8 RUNIC LETTER ANSUZ A)
public var isLetter: Bool {
return _firstScalar.properties.isAlphabetic
}
- /// Perform case conversion to uppercase
+ /// Returns an uppercased version of this character.
///
- /// Examples:
- /// * "é" (U+0065 LATIN SMALL LETTER E, U+0301 COMBINING ACUTE ACCENT)
- /// => "É" (U+0045 LATIN CAPITAL LETTER E, U+0301 COMBINING ACUTE ACCENT)
- /// * "и" (U+0438 CYRILLIC SMALL LETTER I)
- /// => "И" (U+0418 CYRILLIC CAPITAL LETTER I)
- /// * "π" (U+03C0 GREEK SMALL LETTER PI)
- /// => "Π" (U+03A0 GREEK CAPITAL LETTER PI)
- /// * "ß" (U+00DF LATIN SMALL LETTER SHARP S)
- /// => "SS" (U+0053 LATIN CAPITAL LETTER S, U+0053 LATIN CAPITAL LETTER S)
+ /// Because case conversion can result in multiple characters, the result
+ /// of `uppercased()` is a string.
///
- /// Note: Returns a String as case conversion can result in multiple
- /// Characters.
+ /// let chars: [Character] = ["e", "é", "и", "π", "ß", "1"]
+ /// for ch in chars {
+ /// print(ch, "-->", ch.uppercased())
+ /// }
+ /// // e --> E
+ /// // é --> É
+ /// // и --> И
+ /// // π --> Π
+ /// // ß --> SS
+ /// // 1 --> 1
public func uppercased() -> String { return String(self).uppercased() }
- /// Perform case conversion to lowercase
+ /// Returns a lowercased version of this character.
///
- /// Examples:
- /// * "É" (U+0045 LATIN CAPITAL LETTER E, U+0301 COMBINING ACUTE ACCENT)
- /// => "é" (U+0065 LATIN SMALL LETTER E, U+0301 COMBINING ACUTE ACCENT)
- /// * "И" (U+0418 CYRILLIC CAPITAL LETTER I)
- /// => "и" (U+0438 CYRILLIC SMALL LETTER I)
- /// * "Π" (U+03A0 GREEK CAPITAL LETTER PI)
- /// => "π" (U+03C0 GREEK SMALL LETTER PI)
+ /// Because case conversion can result in multiple characters, the result
+ /// of `lowercased()` is a string.
///
- /// Note: Returns a String as case conversion can result in multiple
- /// Characters.
+ /// let chars: [Character] = ["E", "É", "И", "Π", "1"]
+ /// for ch in chars {
+ /// print(ch, "-->", ch.lowercased())
+ /// }
+ /// // E --> e
+ /// // É --> é
+ /// // И --> и
+ /// // Π --> π
+ /// // 1 --> 1
public func lowercased() -> String { return String(self).lowercased() }
@usableFromInline
@@ -191,16 +235,14 @@
@usableFromInline
internal var _isLowercased: Bool { return String(self) == self.lowercased() }
- /// Whether this Character is considered uppercase.
+ /// A Boolean value indicating whether this character is considered uppercase.
///
- /// Uppercase Characters vary under case-conversion to lowercase, but not when
- /// converted to uppercase.
+ /// Uppercase characters vary under case-conversion to lowercase, but not when
+ /// converted to uppercase. The following characters are all uppercase:
///
- /// Examples:
- /// * "É" (U+0045 LATIN CAPITAL LETTER E, U+0301 COMBINING ACUTE ACCENT)
- /// * "И" (U+0418 CYRILLIC CAPITAL LETTER I)
- /// * "Π" (U+03A0 GREEK CAPITAL LETTER PI)
- ///
+ /// - "É" (U+0045 LATIN CAPITAL LETTER E, U+0301 COMBINING ACUTE ACCENT)
+ /// - "И" (U+0418 CYRILLIC CAPITAL LETTER I)
+ /// - "Π" (U+03A0 GREEK CAPITAL LETTER PI)
@inlinable
public var isUppercase: Bool {
if _fastPath(_isSingleScalar && _firstScalar.properties.isUppercase) {
@@ -209,16 +251,14 @@
return _isUppercased && isCased
}
- /// Whether this Character is considered lowercase.
+ /// A Boolean value indicating whether this character is considered lowercase.
///
- /// Lowercase Characters vary under case-conversion to uppercase, but not when
- /// converted to lowercase.
+ /// Lowercase characters change when converted to uppercase, but not when
+ /// converted to lowercase. The following characters are all lowercase:
///
- /// Examples:
- /// * "é" (U+0065 LATIN SMALL LETTER E, U+0301 COMBINING ACUTE ACCENT)
- /// * "и" (U+0438 CYRILLIC SMALL LETTER I)
- /// * "π" (U+03C0 GREEK SMALL LETTER PI)
- ///
+ /// - "é" (U+0065 LATIN SMALL LETTER E, U+0301 COMBINING ACUTE ACCENT)
+ /// - "и" (U+0438 CYRILLIC SMALL LETTER I)
+ /// - "π" (U+03C0 GREEK SMALL LETTER PI)
@inlinable
public var isLowercase: Bool {
if _fastPath(_isSingleScalar && _firstScalar.properties.isLowercase) {
@@ -227,7 +267,8 @@
return _isLowercased && isCased
}
- /// Whether this Character changes under any form of case conversion.
+ /// A Boolean value indicating whether this character changes under any form
+ /// of case conversion.
@inlinable
public var isCased: Bool {
if _fastPath(_isSingleScalar && _firstScalar.properties.isCased) {
@@ -236,53 +277,64 @@
return !_isUppercased || !_isLowercased
}
- /// Whether this Character represents a symbol
+ /// A Boolean value indicating whether this character represents a symbol.
///
- /// Examples:
- /// * "®" (U+00AE REGISTERED SIGN)
- /// * "⌹" (U+2339 APL FUNCTIONAL SYMBOL QUAD DIVIDE)
- /// * "⡆" (U+2846 BRAILLE PATTERN DOTS-237)
+ /// This property is `true` only for characters composed of scalars in the
+ /// "Math_Symbol", "Currency_Symbol", "Modifier_Symbol", or "Other_Symbol"
+ /// categories in the
+ /// [Unicode Standard](https://unicode.org/reports/tr44/#General_Category_Values).
///
+ /// For example, the following characters all represent symbols:
+ ///
+ /// - "®" (U+00AE REGISTERED SIGN)
+ /// - "⌹" (U+2339 APL FUNCTIONAL SYMBOL QUAD DIVIDE)
+ /// - "⡆" (U+2846 BRAILLE PATTERN DOTS-237)
public var isSymbol: Bool {
return _firstScalar.properties.generalCategory._isSymbol
}
- /// Whether this Character represents a symbol used mathematical formulas
+ /// A Boolean value indicating whether this character represents a symbol
+ /// that naturally appears in mathematical contexts.
///
- /// Examples:
- /// * "+" (U+002B PLUS SIGN)
- /// * "∫" (U+222B INTEGRAL)
- /// * "ϰ" (U+03F0 GREEK KAPPA SYMBOL)
+ /// For example, the following characters all represent math symbols:
///
- /// Note: This is not a strict subset of isSymbol. This includes characters
- /// used both as letters and commonly in mathematical formulas. For example,
- /// "ϰ" (U+03F0 GREEK KAPPA SYMBOL) is considered a both mathematical symbol
- /// and a letter.
+ /// - "+" (U+002B PLUS SIGN)
+ /// - "∫" (U+222B INTEGRAL)
+ /// - "ϰ" (U+03F0 GREEK KAPPA SYMBOL)
///
+ /// The set of characters that have an `isMathSymbol` value of `true` is not
+ /// a strict subset of those for which `isSymbol` is `true`. This includes
+ /// characters used both as letters and commonly in mathematical formulas.
+ /// For example, "ϰ" (U+03F0 GREEK KAPPA SYMBOL) is considered both a
+ /// mathematical symbol and a letter.
+ ///
+ /// This property corresponds to the "Math" property in the
+ /// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isMathSymbol: Bool {
return _firstScalar.properties.isMath
}
- /// Whether this Character represents a currency symbol
+ /// A Boolean value indicating whether this character represents a currency
+ /// symbol.
///
- /// Examples:
- /// * "$" (U+0024 DOLLAR SIGN)
- /// * "¥" (U+00A5 YEN SIGN)
- /// * "€" (U+20AC EURO SIGN)
+ /// For example, the following characters all represent currency symbols:
///
+ /// - "$" (U+0024 DOLLAR SIGN)
+ /// - "¥" (U+00A5 YEN SIGN)
+ /// - "€" (U+20AC EURO SIGN)
public var isCurrencySymbol: Bool {
return _firstScalar.properties.generalCategory == .currencySymbol
}
- /// Whether this Character represents punctuation
+ /// A Boolean value indicating whether this character represents punctuation.
///
- /// Examples:
- /// * "!" (U+0021 EXCLAMATION MARK)
- /// * "؟" (U+061F ARABIC QUESTION MARK)
- /// * "…" (U+2026 HORIZONTAL ELLIPSIS)
- /// * "—" (U+2014 EM DASH)
- /// * "“" (U+201C LEFT DOUBLE QUOTATION MARK)
+ /// For example, the following characters all represent punctuation:
///
+ /// - "!" (U+0021 EXCLAMATION MARK)
+ /// - "؟" (U+061F ARABIC QUESTION MARK)
+ /// - "…" (U+2026 HORIZONTAL ELLIPSIS)
+ /// - "—" (U+2014 EM DASH)
+ /// - "“" (U+201C LEFT DOUBLE QUOTATION MARK)
public var isPunctuation: Bool {
return _firstScalar.properties.generalCategory._isPunctuation
}
diff --git a/stdlib/public/core/CompilerProtocols.swift b/stdlib/public/core/CompilerProtocols.swift
index d055c2c..fa2fc4f 100644
--- a/stdlib/public/core/CompilerProtocols.swift
+++ b/stdlib/public/core/CompilerProtocols.swift
@@ -709,45 +709,49 @@
/// print(message)
/// // Prints "One cookie: $2, 3 cookies: $6."
///
-/// Extending default interpolation behavior
-/// ========================================
+/// Extending the Default Interpolation Behavior
+/// ============================================
///
-/// Clients which want to add new interpolation behavior to existing types
-/// should extend `DefaultStringInterpolation`, the type which implements
-/// interpolation for types like `String` and `Substring`, to add an overload of
-/// `appendInterpolation(_:)` with their new behavior. See the
-/// `DefaultStringInterpolation` and `StringInterpolationProtocol` documentation
-/// for more details.
-///
-/// Creating a type which supports default string interpolation
-/// ===========================================================
-///
-/// Clients which want to create new types supporting string literals and
-/// interpolation, but which do not need any custom behavior, should conform
-/// their type to `ExpressibleByStringInterpolation` and implement an
-/// `init(stringLiteral: String)` method. Swift will automatically use
-/// `DefaultStringInterpolation` and provide an `init(stringInterpolation:)`
-/// implementation which passes the interpolated literal's contents to
-/// `init(stringLiteral:)`, so you won't need to implement anything special.
+/// Add new interpolation behavior to existing types by extending
+/// `DefaultStringInterpolation`, the type that implements interpolation for
+/// types like `String` and `Substring`, to add an overload of
+/// `appendInterpolation(_:)` with their new behavior.
///
-/// Creating a type which supports custom string interpolation
-/// ==========================================================
+/// For more information, see the `DefaultStringInterpolation` and
+/// `StringInterpolationProtocol` documentation.
///
-/// If a conforming type wants to differentiate between literal and interpolated
-/// segments, restrict the types which can be interpolated into it, support
-/// different interpolators from the ones on `String`, or avoid constructing a
-/// `String` containing the data, it must specify a custom `StringInterpolation`
-/// associated type. This type must conform to `StringInterpolationProtocol` and
-/// must have a matching `StringLiteralType`.
+/// Creating a Type That Supports the Default String Interpolation
+/// ==============================================================
+///
+/// To create a new type that supports string literals and interpolation, but
+/// that doesn't need any custom behavior, conform the type to
+/// `ExpressibleByStringInterpolation` and implement the
+/// `init(stringLiteral: String)` initializer declared by the
+/// `ExpressibleByStringLiteral` protocol. Swift will automatically use
+/// `DefaultStringInterpolation` as the interpolation type and provide an
+/// implementation for `init(stringInterpolation:)` that passes the
+/// interpolated literal's contents to `init(stringLiteral:)`, so you don't
+/// need to implement anything specific to this protocol.
///
-/// See the `StringLiteralProtocol` documentation for more details about how to
-/// do this.
+/// Creating a Type That Supports Custom String Interpolation
+/// =========================================================
+///
+/// If you want a conforming type to differentiate between literal and
+/// interpolated segments, restrict the types that can be interpolated,
+/// support different interpolators from the ones on `String`, or avoid
+/// constructing a `String` containing the data, the type must specify a custom
+/// `StringInterpolation` associated type. This type must conform to
+/// `StringInterpolationProtocol` and have a matching `StringLiteralType`.
+///
+/// For more information, see the `StringInterpolationProtocol` documentation.
public protocol ExpressibleByStringInterpolation
: ExpressibleByStringLiteral {
/// The type each segment of a string literal containing interpolations
- /// should be appended to. Its `StringLiteralType` should match the
- /// `StringLiteralType` of this type.
+ /// should be appended to.
+ ///
+ /// The `StringLiteralType` of an interpolation type must match the
+ /// `StringLiteralType` of the conforming type.
associatedtype StringInterpolation : StringInterpolationProtocol
= DefaultStringInterpolation
where StringInterpolation.StringLiteralType == StringLiteralType
@@ -770,7 +774,7 @@
/// Creates a new instance from an interpolated string literal.
///
- /// Do not call this initializer directly. It is used by the compiler when
+ /// Don't call this initializer directly. It's used by the compiler when
/// you create a string using string interpolation. Instead, use string
/// interpolation to create a new string by including values, literals,
/// variables, or expressions enclosed in parentheses, prefixed by a
@@ -782,14 +786,13 @@
/// If one cookie costs \(price) dollars, \
/// \(number) cookies cost \(price * number) dollars.
/// """
- /// print(message)
- /// // Prints "If one cookie costs 2 dollars, 3 cookies cost 6 dollars."
+ /// // message == "If one cookie costs 2 dollars, 3 cookies cost 6 dollars."
public init(stringInterpolation: DefaultStringInterpolation) {
self.init(stringLiteral: stringInterpolation.make())
}
}
-/// Represents the contents of a string literal with interpolations while it is
+/// Represents the contents of a string literal with interpolations while it's
/// being built up.
///
/// Each `ExpressibleByStringInterpolation` type has an associated
@@ -809,60 +812,78 @@
/// The `StringInterpolation` type is responsible for collecting the segments
/// passed to its `appendLiteral(_:)` and `appendInterpolation` methods and
/// assembling them into a whole, converting as necessary. Once all of the
-/// segments have been appended, the interpolation will be passed to an
+/// segments are appended, the interpolation is passed to an
/// `init(stringInterpolation:)` initializer on the type being created, which
/// must extract the accumulated data from the `StringInterpolation`.
///
-/// In simple cases, types conforming to `ExpressibleByStringInterpolation`
-/// can use `DefaultStringInterpolation` instead of writing their own. All they
-/// must do is conform to `ExpressibleByStringInterpolation` and implement
-/// `init(stringLiteral: String)`; interpolated string literals will then go
-/// through that initializer just as any other string literal would.
+/// In simple cases, you can use `DefaultStringInterpolation` as the
+/// interpolation type for types that conform to the
+/// `ExpressibleByStringLiteral` protocol. To use the default interpolation,
+/// conform a type to `ExpressibleByStringInterpolation` and implement
+/// `init(stringLiteral: String)`. Values in interpolations are converted to
+/// strings, and then passed to that initializer just like any other string
+/// literal.
///
-/// The `appendInterpolation` Method
-/// ================================
-///
-/// Each interpolated segment is translated into a call to a
-/// `StringInterpolationProtocol.appendInterpolation(...)` method, with the
-/// contents of the interpolation's parentheses treated as the call's argument
-/// list. That argument list can include multiple arguments and argument labels.
-/// For example:
-///
-/// | If you write... | Swift calls... |
-/// |---------------- | --------------------------------- |
-/// | `\(x)` | `appendInterpolation(x)` |
-/// | `\(x, y)` | `appendInterpolation(x, y)` |
-/// | `\(foo: x)` | `appendInterpolation(foo: x)` |
-/// | `\(x, foo: y)` | `appendInterpolation(x, foo: y)` |
-///
-/// `appendInterpolation` methods should return `Void` and should not be
-/// `static`. They otherwise support virtually all features of methods: they can
-/// have any number of parameters, can specify labels for any or all of them,
-/// can provide default values for parameters, can have variadic parameters, and
-/// can have parameters with generic types. Most importantly, they can be
-/// overloaded, so a `StringInterpolationProtocol`-conforming type can provide
-/// several different `appendInterpolation` methods with different behaviors.
-/// `appendInterpolation` methods can also throw; when a user uses one of these,
-/// they must mark the string literal with `try` or one of its variants.
+/// Handling String Interpolations
+/// ==============================
+///
+/// With a custom interpolation type, each interpolated segment is translated
+/// into a call to a special `appendInterpolation` method. The contents of
+/// the interpolation's parentheses are treated as the call's argument list.
+/// That argument list can include multiple arguments and argument labels.
+///
+/// The following examples show how string interpolations are translated into
+/// calls to `appendInterpolation`:
+///
+/// - `\(x)` translates to `appendInterpolation(x)`
+/// - `\(x, y)` translates to `appendInterpolation(x, y)`
+/// - `\(foo: x)` translates to `appendInterpolation(foo: x)`
+/// - `\(x, foo: y)` translates to `appendInterpolation(x, foo: y)`
+///
+/// The `appendInterpolation` methods in your custom type must be mutating
+/// instance methods that return `Void`. This code shows a custom interpolation
+/// type's declaration of an `appendInterpolation` method that provides special
+/// validation for user input:
+///
+/// extension MyString.StringInterpolation {
+/// mutating func appendInterpolation(validating input: String) {
+/// // Perform validation of `input` and store for later use
+/// }
+/// }
+///
+/// To use this interpolation method, create a string literal with an
+/// interpolation using the `validating` parameter label.
+///
+/// let userInput = readLine() ?? ""
+/// let myString = "The user typed '\(validating: userInput)'." as MyString
+///
+/// `appendInterpolation` methods support virtually all features of methods:
+/// they can have any number of parameters, can specify labels for any or all
+/// of their parameters, can provide default values, can have variadic
+/// parameters, and can have parameters with generic types. Most importantly,
+/// they can be overloaded, so a type that conforms to
+/// `StringInterpolationProtocol` can provide several different
+/// `appendInterpolation` methods with different behaviors. An
+/// `appendInterpolation` method can also throw; when a user writes a literal
+/// with one of these interpolations, they must mark the string literal with
+/// `try` or one of its variants.
public protocol StringInterpolationProtocol {
/// The type that should be used for literal segments.
associatedtype StringLiteralType : _ExpressibleByBuiltinStringLiteral
/// Creates an empty instance ready to be filled with string literal content.
///
- /// Do not call this initializer directly. Instead, initialize a variable or
+ /// Don't call this initializer directly. Instead, initialize a variable or
/// constant using a string literal with interpolated expressions.
///
/// Swift passes this initializer a pair of arguments specifying the size of
/// the literal segments and the number of interpolated segments. Use this
- /// information to estimate the amount of storage you will need and
- /// pre-allocate it with a method like
- /// `RangeReplaceableCollection.reserveCapacity(_:)`.
+ /// information to estimate the amount of storage you will need.
///
/// - Parameter literalCapacity: The approximate size of all literal segments
/// combined. This is meant to be passed to `String.reserveCapacity(_:)`;
- /// it may be slightly larger or smaller than the sum of `String.count`
- /// called on each literal segment.
+ /// it may be slightly larger or smaller than the sum of the counts of each
+ /// literal segment.
/// - Parameter interpolationCount: The number of interpolations which will be
/// appended. Use this value to estimate how much additional capacity will
/// be needed for the interpolated segments.
@@ -870,15 +891,15 @@
/// Appends a literal segment to the interpolation.
///
- /// Do not call this method directly. Instead, initialize a variable or
+ /// Don't call this method directly. Instead, initialize a variable or
/// constant using a string literal with interpolated expressions.
///
- /// Interpolated expressions do not pass through this method; instead, Swift
- /// selects an overload of `appendInterpolation`. See the top-level
- /// `StringInterpolationProtocol` documentation for more details.
+ /// Interpolated expressions don't pass through this method; instead, Swift
+ /// selects an overload of `appendInterpolation`. For more information, see
+ /// the top-level `StringInterpolationProtocol` documentation.
///
/// - Parameter literal: A string literal containing the characters
- /// that appear next in the string literal.
+ /// that appear next in the string literal.
mutating func appendLiteral(_ literal: StringLiteralType)
// Informal requirement: Any desired appendInterpolation overloads, e.g.:
diff --git a/stdlib/public/core/Dictionary.swift b/stdlib/public/core/Dictionary.swift
index 65fa9cd..9f0a733 100644
--- a/stdlib/public/core/Dictionary.swift
+++ b/stdlib/public/core/Dictionary.swift
@@ -921,10 +921,10 @@
}
/// Returns a new dictionary containing only the key-value pairs that have
- /// non-`nil` values as the result from the transform by the given closure.
+ /// non-`nil` values as the result of transformation by the given closure.
///
- /// Use this method to receive a dictionary of non-optional values when your
- /// transformation can produce an optional value.
+ /// Use this method to receive a dictionary with non-optional values when
+ /// your transformation produces optional values.
///
/// In this example, note the difference in the result of using `mapValues`
/// and `compactMapValues` with a transformation that returns an optional
diff --git a/stdlib/public/core/Integers.swift b/stdlib/public/core/Integers.swift
index fbf687b..bd1cb6e 100644
--- a/stdlib/public/core/Integers.swift
+++ b/stdlib/public/core/Integers.swift
@@ -27,12 +27,45 @@
//===--- AdditiveArithmetic -----------------------------------------------===//
//===----------------------------------------------------------------------===//
-// FIXME: Add doc comment.
+/// A type with values that support addition and subtraction.
+///
+/// The `AdditiveArithmetic` protocol provides a suitable basis for additive
+/// arithmetic on scalar values, such as integers and floating-point numbers,
+/// or vectors. You can write generic methods that operate on any numeric type
+/// in the standard library by using the `AdditiveArithmetic` protocol as a
+/// generic constraint.
+///
+/// The following code declares a method that calculates the total of any
+/// sequence with `Numeric` elements.
+///
+/// extension Sequence where Element: AdditiveArithmetic {
+/// func sum() -> Element {
+/// return reduce(.zero, +)
+/// }
+/// }
+///
+/// The `sum()` method is now available on any sequence with values that
+/// conform to `AdditiveArithmetic`, whether it is an array of `Double` or a
+/// range of `Int`.
+///
+/// let arraySum = [1.1, 2.2, 3.3, 4.4, 5.5].sum()
+/// // arraySum == 16.5
+///
+/// let rangeSum = (1..<10).sum()
+/// // rangeSum == 45
+///
+/// Conforming to the AdditiveArithmetic Protocol
+/// =============================================
+///
+/// To add `AdditiveArithmetic` protocol conformance to your own custom type,
+/// implement the required operators, and provide a static `zero` property
+/// using a type that can represent the magnitude of any value of your custom
+/// type.
public protocol AdditiveArithmetic : Equatable {
/// The zero value.
///
- /// - Note: Zero is the identity element for addition; for any value,
- /// `x + .zero == x` and `.zero + x == x`.
+ /// Zero is the identity element for addition. For any value,
+ /// `x + .zero == x` and `.zero + x == x`.
static var zero: Self { get }
/// Adds two values and produces their sum.
@@ -96,6 +129,10 @@
}
public extension AdditiveArithmetic where Self : ExpressibleByIntegerLiteral {
+ /// The zero value.
+ ///
+ /// Zero is the identity element for addition. For any value,
+ /// `x + .zero == x` and `.zero + x == x`.
static var zero: Self {
return 0
}
@@ -105,41 +142,41 @@
//===--- Numeric ----------------------------------------------------------===//
//===----------------------------------------------------------------------===//
-// FIXME: Update comment based on the `AdditiveArithmetic` change.
-/// Declares methods backing binary arithmetic operators--such as `+`, `-` and
-/// `*`--and their mutating counterparts.
+/// A type with values that support multiplication.
///
/// The `Numeric` protocol provides a suitable basis for arithmetic on
/// scalar values, such as integers and floating-point numbers. You can write
/// generic methods that operate on any numeric type in the standard library
/// by using the `Numeric` protocol as a generic constraint.
///
-/// The following example declares a method that calculates the total of any
-/// sequence with `Numeric` elements.
+/// The following example extends `Sequence` with a method that returns an
+/// array with the sequence's values multiplied by two.
///
/// extension Sequence where Element: Numeric {
-/// func sum() -> Element {
-/// return reduce(0, +)
+/// func doublingAll() -> [Element] {
+/// return map { $0 * 2 }
/// }
/// }
///
-/// The `sum()` method is now available on any sequence or collection with
-/// numeric values, whether it is an array of `Double` or a countable range of
-/// `Int`.
+/// With this extension, any sequence with elements that conform to `Numeric`
+/// has the `doublingAll()` method. For example, you can double the elements of
+/// an array of doubles or a range of integers:
///
-/// let arraySum = [1.1, 2.2, 3.3, 4.4, 5.5].sum()
-/// // arraySum == 16.5
+/// let observations = [1.5, 2.0, 3.25, 4.875, 5.5]
+/// let doubledObservations = observations.doublingAll()
+/// // doubledObservations == [3.0, 4.0, 6.5, 9.75, 11.0]
///
-/// let rangeSum = (1..<10).sum()
-/// // rangeSum == 45
+/// let integers = 0..<8
+/// let doubledIntegers = integers.doublingAll()
+/// // doubledIntegers == [0, 2, 4, 6, 8, 10, 12, 14]
///
/// Conforming to the Numeric Protocol
-/// =====================================
+/// ==================================
///
/// To add `Numeric` protocol conformance to your own custom type, implement
-/// the required mutating methods. Extensions to `Numeric` provide default
-/// implementations for the protocol's nonmutating methods based on the
-/// mutating variants.
+/// the required initializer and operators, and provide a `magnitude` property
+/// using a type that can represent the magnitude of any value of your custom
+/// type.
public protocol Numeric : AdditiveArithmetic, ExpressibleByIntegerLiteral {
/// Creates a new instance from the given integer, if it can be represented
/// exactly.
@@ -216,7 +253,7 @@
/// `Numeric` protocol to include a value's additive inverse.
///
/// Conforming to the SignedNumeric Protocol
-/// ===========================================
+/// ========================================
///
/// Because the `SignedNumeric` protocol provides default implementations of
/// both of its required methods, you don't need to do anything beyond
@@ -1163,19 +1200,20 @@
func quotientAndRemainder(dividingBy rhs: Self)
-> (quotient: Self, remainder: Self)
- /// Returns true if this value is a multiple of `other`, and false otherwise.
+ /// Returns `true` if this value is a multiple of the given value, and `false`
+ /// otherwise.
///
- /// For two integers a and b, a is a multiple of b if there exists a third
- /// integer q such that a = q*b. For example, 6 is a multiple of 3, because
- /// 6 = 2*3, and zero is a multiple of everything, because 0 = 0*x, for any
- /// integer x.
+ /// For two integers *a* and *b*, *a* is a multiple of *b* if there exists a
+ /// third integer *q* such that _a = q*b_. For example, *6* is a multiple of
+ /// *3* because _6 = 2*3_. Zero is a multiple of everything because _0 = 0*x_
+ /// for any integer *x*.
///
/// Two edge cases are worth particular attention:
/// - `x.isMultiple(of: 0)` is `true` if `x` is zero and `false` otherwise.
/// - `T.min.isMultiple(of: -1)` is `true` for signed integer `T`, even
- /// though the quotient `T.min / -1` is not representable in type `T`.
+ /// though the quotient `T.min / -1` isn't representable in type `T`.
///
- /// - Parameter other: the value to test.
+ /// - Parameter other: The value to test.
func isMultiple(of other: Self) -> Bool
/// Returns `-1` if this value is negative and `1` if it's positive;
diff --git a/stdlib/public/core/Result.swift b/stdlib/public/core/Result.swift
index fdd742e..c6386bf 100644
--- a/stdlib/public/core/Result.swift
+++ b/stdlib/public/core/Result.swift
@@ -27,7 +27,7 @@
/// instance when it represents a success. The following example transforms
/// the integer success value of a result into a string:
///
- /// func getNextInteger() -> Result<Int, Error> { ... }
+ /// func getNextInteger() -> Result<Int, Error> { /* ... */ }
///
/// let integerResult = getNextInteger()
/// // integerResult == .success(5)
@@ -66,7 +66,7 @@
/// }
/// }
///
- /// let result: Result<Int, Error> = ...
+ /// let result: Result<Int, Error> = // ...
/// // result == .failure(<error value>)
/// let resultWithDatedError = result.mapError({ e in DatedError(e) })
/// // result == .failure(DatedError(error: <error value>, date: <date>))
@@ -136,7 +136,7 @@
/// }
/// // Prints "The value is 5."
///
- /// - Returns: The success value, if the instance represent a success.
+ /// - Returns: The success value, if the instance represents a success.
/// - Throws: The failure value, if the instance represents a failure.
public func get() throws -> Success {
switch self {
diff --git a/stdlib/public/core/SIMDVector.swift b/stdlib/public/core/SIMDVector.swift
index e1ccb42..79d0d7d 100644
--- a/stdlib/public/core/SIMDVector.swift
+++ b/stdlib/public/core/SIMDVector.swift
@@ -15,25 +15,30 @@
infix operator .|= : AssignmentPrecedence
prefix operator .!
-/// A SIMD vector type that may not have any computational operations.
+/// A type that provides storage for a SIMD vector type.
///
-/// This protocol only defines a storage layout and provides elementwise
-/// accesses. Computational operations are defined on SIMDVector, which
-/// refines this protocol, or on the concrete types that conform.
+/// The `SIMDStorage` protocol defines a storage layout and provides
+/// elementwise accesses. Computational operations are defined on the `SIMD`
+/// protocol, which refines this protocol, and on the concrete types that
+/// conform to `SIMD`.
public protocol SIMDStorage {
/// The type of scalars in the vector space.
associatedtype Scalar : Hashable
- /// The number of scalars/elements in the vector.
+ /// The number of scalars, or elements, in the vector.
var scalarCount: Int { get }
- /// A vector with zero in all lanes.
+ /// Creates a vector with zero in all lanes.
init()
- /// Element access to the vector.
+ /// Accesses the element at the specified index.
+ ///
+ /// - Parameter index: The index of the element to access. `index` must be in
+ /// the range `0..<scalarCount`.
subscript(index: Int) -> Scalar { get set }
}
+/// A type that can be used as an element in a SIMD vector.
public protocol SIMDScalar {
associatedtype SIMDMaskScalar : SIMDScalar & FixedWidthInteger & SignedInteger
associatedtype SIMD2Storage : SIMDStorage where SIMD2Storage.Scalar == Self
@@ -44,6 +49,7 @@
associatedtype SIMD64Storage : SIMDStorage where SIMD64Storage.Scalar == Self
}
+/// A SIMD vector of a fixed number of elements.
public protocol SIMD : SIMDStorage,
Hashable,
CustomStringConvertible,
@@ -58,14 +64,14 @@
@_transparent
var indices: Range<Int> { return 0 ..< scalarCount }
- /// A vector with value in all lanes.
+ /// A vector with the specified value in all lanes.
@_transparent
init(repeating value: Scalar) {
self.init()
for i in indices { self[i] = value }
}
- /// Conformance to Equatable
+ /// Returns a Boolean value indicating whether two vectors are equal.
@_transparent
static func ==(lhs: Self, rhs: Self) -> Bool {
var result = true
@@ -73,20 +79,20 @@
return result
}
- /// Conformance to Hashable
+ /// Hashes the elements of the vector using the given hasher.
@inlinable
func hash(into hasher: inout Hasher) {
for i in indices { hasher.combine(self[i]) }
}
- /// Conformance to CustomStringConvertible
+ /// A textual description of the vector.
var description: String {
get {
return "\(Self.self)(" + indices.map({"\(self[$0])"}).joined(separator: ", ") + ")"
}
}
- /// Pointwise equality
+ /// Returns a vector mask with the result of a pointwise equality comparison.
@_transparent
static func .==(lhs: Self, rhs: Self) -> SIMDMask<MaskStorage> {
var result = SIMDMask<MaskStorage>()
@@ -94,6 +100,8 @@
return result
}
+ /// Returns a vector mask with the result of a pointwise inequality
+ /// comparison.
@_transparent
static func .!=(lhs: Self, rhs: Self) -> SIMDMask<MaskStorage> {
var result = SIMDMask<MaskStorage>()
@@ -101,18 +109,26 @@
return result
}
- /// Replaces elements of this vector with `other` in the lanes where
- /// `mask` is `true`.
+ /// Replaces elements of this vector with elements of `other` in the lanes
+ /// where `mask` is `true`.
@_transparent
mutating func replace(with other: Self, where mask: SIMDMask<MaskStorage>) {
for i in indices { self[i] = mask[i] ? other[i] : self[i] }
}
+ /// Creates a vector from the specified elements.
+ ///
+ /// - Parameter scalars: The elements to use in the vector. `scalars` must
+ /// have the same number of elements as the vector type.
@inlinable
init(arrayLiteral scalars: Scalar...) {
self.init(scalars)
}
+ /// Creates a vector from the given sequence.
+ ///
+ /// - Parameter scalars: The elements to use in the vector. `scalars` must
+ /// have the same number of elements as the vector type.
@inlinable
init<S: Sequence>(_ scalars: S) where S.Element == Scalar {
self.init()
@@ -133,7 +149,8 @@
// Implementations of comparison operations. These should eventually all
// be replaced with @_semantics to lower directly to vector IR nodes.
public extension SIMD where Scalar : Comparable {
- /// Pointwise less than
+ /// Returns a vector mask with the result of a pointwise less than
+ /// comparison.
@_transparent
static func .<(lhs: Self, rhs: Self) -> SIMDMask<MaskStorage> {
var result = SIMDMask<MaskStorage>()
@@ -141,7 +158,8 @@
return result
}
- /// Pointwise less than or equal to
+ /// Returns a vector mask with the result of a pointwise less than or equal
+ /// comparison.
@_transparent
static func .<=(lhs: Self, rhs: Self) -> SIMDMask<MaskStorage> {
var result = SIMDMask<MaskStorage>()
@@ -153,16 +171,27 @@
// These operations should never need @_semantics; they should be trivial
// wrappers around the core operations defined above.
public extension SIMD {
+ /// Returns a vector mask with the result of a pointwise equality comparison.
@_transparent static func .==(lhs: Scalar, rhs: Self) -> SIMDMask<MaskStorage> { return Self(repeating: lhs) .== rhs }
+
+ /// Returns a vector mask with the result of a pointwise inequality comparison.
@_transparent static func .!=(lhs: Scalar, rhs: Self) -> SIMDMask<MaskStorage> { return Self(repeating: lhs) .!= rhs }
+
+ /// Returns a vector mask with the result of a pointwise equality comparison.
@_transparent static func .==(lhs: Self, rhs: Scalar) -> SIMDMask<MaskStorage> { return lhs .== Self(repeating: rhs) }
+
+ /// Returns a vector mask with the result of a pointwise inequality comparison.
@_transparent static func .!=(lhs: Self, rhs: Scalar) -> SIMDMask<MaskStorage> { return lhs .!= Self(repeating: rhs) }
+ /// Replaces elements of this vector with `other` in the lanes where `mask`
+ /// is `true`.
@_transparent
mutating func replace(with other: Scalar, where mask: SIMDMask<MaskStorage>) {
replace(with: Self(repeating: other), where: mask)
}
+ /// Returns a copy of this vector, with elements replaced by elements of
+ /// `other` in the lanes where `mask` is `true`.
@_transparent
func replacing(with other: Self, where mask: SIMDMask<MaskStorage>) -> Self {
var result = self
@@ -170,6 +199,8 @@
return result
}
+ /// Returns a copy of this vector, with elements `other` in the lanes where
+ /// `mask` is `true`.
@_transparent
func replacing(with other: Scalar, where mask: SIMDMask<MaskStorage>) -> Self {
return replacing(with: Self(repeating: other), where: mask)
@@ -177,21 +208,51 @@
}
public extension SIMD where Scalar : Comparable {
+ /// Returns a vector mask with the result of a pointwise greater than or
+ /// equal comparison.
@_transparent static func .>=(lhs: Self, rhs: Self) -> SIMDMask<MaskStorage> { return rhs .<= lhs }
+
+ /// Returns a vector mask with the result of a pointwise greater than
+ /// comparison.
@_transparent static func .>(lhs: Self, rhs: Self) -> SIMDMask<MaskStorage> { return rhs .< lhs }
+
+ /// Returns a vector mask with the result of a pointwise less than comparison.
@_transparent static func .<(lhs: Scalar, rhs: Self) -> SIMDMask<MaskStorage> { return Self(repeating: lhs) .< rhs }
+
+ /// Returns a vector mask with the result of a pointwise less than or equal
+ /// comparison.
@_transparent static func .<=(lhs: Scalar, rhs: Self) -> SIMDMask<MaskStorage> { return Self(repeating: lhs) .<= rhs }
+
+ /// Returns a vector mask with the result of a pointwise greater than or
+ /// equal comparison.
@_transparent static func .>=(lhs: Scalar, rhs: Self) -> SIMDMask<MaskStorage> { return Self(repeating: lhs) .>= rhs }
+
+ /// Returns a vector mask with the result of a pointwise greater than
+ /// comparison.
@_transparent static func .>(lhs: Scalar, rhs: Self) -> SIMDMask<MaskStorage> { return Self(repeating: lhs) .> rhs }
+
+ /// Returns a vector mask with the result of a pointwise less than comparison.
@_transparent static func .<(lhs: Self, rhs: Scalar) -> SIMDMask<MaskStorage> { return lhs .< Self(repeating: rhs) }
+
+ /// Returns a vector mask with the result of a pointwise less than or equal
+ /// comparison.
@_transparent static func .<=(lhs: Self, rhs: Scalar) -> SIMDMask<MaskStorage> { return lhs .<= Self(repeating: rhs) }
+
+ /// Returns a vector mask with the result of a pointwise greater than or
+ /// equal comparison.
@_transparent static func .>=(lhs: Self, rhs: Scalar) -> SIMDMask<MaskStorage> { return lhs .>= Self(repeating: rhs) }
+
+ /// Returns a vector mask with the result of a pointwise greater than
+ /// comparison.
@_transparent static func .>(lhs: Self, rhs: Scalar) -> SIMDMask<MaskStorage> { return lhs .> Self(repeating: rhs) }
}
public extension SIMD where Scalar : FixedWidthInteger {
+ /// A vector with zero in all lanes.
@_transparent static var zero: Self { return Self() }
+ /// Returns a vector with random values from within the specified range in
+ /// all lanes, using the given generator as a source for randomness.
@inlinable
static func random<T: RandomNumberGenerator>(
in range: Range<Scalar>,
@@ -204,12 +265,16 @@
return result
}
+ /// Returns a vector with random values from within the specified range in
+ /// all lanes.
@inlinable
static func random(in range: Range<Scalar>) -> Self {
var g = SystemRandomNumberGenerator()
return Self.random(in: range, using: &g)
}
+ /// Returns a vector with random values from within the specified range in
+ /// all lanes, using the given generator as a source for randomness.
@inlinable
static func random<T: RandomNumberGenerator>(
in range: ClosedRange<Scalar>,
@@ -222,6 +287,8 @@
return result
}
+ /// Returns a vector with random values from within the specified range in
+ /// all lanes.
@inlinable
static func random(in range: ClosedRange<Scalar>) -> Self {
var g = SystemRandomNumberGenerator()
@@ -230,11 +297,14 @@
}
public extension SIMD where Scalar : FloatingPoint {
+ /// A vector with zero in all lanes.
@_transparent static var zero: Self { return Self() }
}
public extension SIMD
where Scalar : BinaryFloatingPoint, Scalar.RawSignificand : FixedWidthInteger {
+ /// Returns a vector with random values from within the specified range in
+ /// all lanes, using the given generator as a source for randomness.
@inlinable
static func random<T: RandomNumberGenerator>(
in range: Range<Scalar>,
@@ -247,12 +317,16 @@
return result
}
+ /// Returns a vector with random values from within the specified range in
+ /// all lanes.
@inlinable
static func random(in range: Range<Scalar>) -> Self {
var g = SystemRandomNumberGenerator()
return Self.random(in: range, using: &g)
}
+ /// Returns a vector with random values from within the specified range in
+ /// all lanes, using the given generator as a source for randomness.
@inlinable
static func random<T: RandomNumberGenerator>(
in range: ClosedRange<Scalar>,
@@ -265,6 +339,8 @@
return result
}
+ /// Returns a vector with random values from within the specified range in
+ /// all lanes.
@inlinable
static func random(in range: ClosedRange<Scalar>) -> Self {
var g = SystemRandomNumberGenerator()
@@ -313,6 +389,8 @@
}
public extension SIMDMask {
+ /// Returns a vector mask with `true` or `false` randomly assigned in each
+ /// lane, using the given generator as a source for randomness.
@inlinable
static func random<T: RandomNumberGenerator>(using generator: inout T) -> SIMDMask {
var result = SIMDMask()
@@ -320,6 +398,8 @@
return result
}
+ /// Returns a vector mask with `true` or `false` randomly assigned in each
+ /// lane.
@inlinable
static func random() -> SIMDMask {
var g = SystemRandomNumberGenerator()
diff --git a/stdlib/public/core/SIMDVectorTypes.swift.gyb b/stdlib/public/core/SIMDVectorTypes.swift.gyb
index a2ed3f5..6a3e13e 100644
--- a/stdlib/public/core/SIMDVectorTypes.swift.gyb
+++ b/stdlib/public/core/SIMDVectorTypes.swift.gyb
@@ -3,10 +3,16 @@
word_bits = int(CMAKE_SIZEOF_VOID_P) * 8
storagescalarCounts = [2,4,8,16,32,64]
vectorscalarCounts = storagescalarCounts + [3]
+spelledNumbers = {
+ 2: 'two', 4: 'four', 8: 'eight', 16: '16', 32: '32', 64: '64',
+ 3: 'three'
+}
+ordinalPositions = ['first', 'second', 'third', 'fourth']
}%
%for n in vectorscalarCounts:
% storageN = 4 if n == 3 else n
+/// A vector of ${spelledNumbers[n]} scalar values.
@_fixed_layout
public struct SIMD${n}<Scalar> : SIMD where Scalar: SIMDScalar {
@@ -14,16 +20,19 @@
public typealias MaskStorage = SIMD${n}<Scalar.SIMDMaskScalar>
+ /// The number of scalars in the vector.
@_transparent
public var scalarCount: Int {
return ${n}
}
+ /// Creates a vector with zero in all lanes.
@_transparent
public init() {
_storage = Scalar.SIMD${storageN}Storage()
}
+ /// Accesses the scalar at the specified position.
public subscript(index: Int) -> Scalar {
@_transparent get {
_precondition(indices.contains(index))
@@ -35,6 +44,7 @@
}
}
+ /// Creates a new vector from the given elements.
@_transparent
public init(${', '.join(['_ v' + str(i) + ': Scalar' for i in range(n)])}) {
self.init()
@@ -44,12 +54,19 @@
}
% if n <= 4:
+ /// Creates a new vector from the given elements.
+ ///
+ /// - Parameters:
+ % for i in range(n):
+ /// - ${'xyzw'[i]}: The ${ordinalPositions[i]} element of the vector.
+ % end
@_transparent
public init(${', '.join([c + ': Scalar' for c in 'xyzw'[:n]])}) {
self.init(${', '.join('xyzw'[:n])})
}
% for i in range(n):
+ /// The ${ordinalPositions[i]} element of the vector.
@_transparent
public var ${'xyzw'[i]}: Scalar {
@_transparent get { return self[${i}]}
@@ -59,6 +76,7 @@
% end
% end
% if n >= 4:
+ /// Creates a new vector from two half-length vectors.
@_transparent
public init(lowHalf: SIMD${n/2}<Scalar>, highHalf: SIMD${n/2}<Scalar>) {
self.init()
@@ -67,6 +85,7 @@
}
% for (half,indx) in [('low','i'), ('high',str(n/2)+'+i'), ('even','2*i'), ('odd','2*i+1')]:
+ /// A half-length vector made up of the ${half} elements of the vector.
public var ${half}Half: SIMD${n/2}<Scalar> {
@inlinable get {
var result = SIMD${n/2}<Scalar>()
@@ -83,6 +102,10 @@
}
public extension SIMD${n} where Scalar : FixedWidthInteger {
+ /// Creates a new vector from the given vector, truncating the bit patterns
+ /// of the given vector's elements if necessary.
+ ///
+ /// - Parameter other: The vector to convert.
@inlinable
init<Other>(truncatingIfNeeded other: SIMD${n}<Other>)
where Other : FixedWidthInteger {
@@ -90,6 +113,10 @@
for i in indices { self[i] = Scalar(truncatingIfNeeded: other[i]) }
}
+ /// Creates a new vector from the given vector, clamping the values of the
+ /// given vector's elements if necessary.
+ ///
+ /// - Parameter other: The vector to convert.
@inlinable
init<Other>(clamping other: SIMD${n}<Other>)
where Other : FixedWidthInteger {
@@ -97,6 +124,13 @@
for i in indices { self[i] = Scalar(clamping: other[i]) }
}
+ /// Creates a new vector from the given vector, rounding the given vector's
+ /// of elements using the specified rounding rule.
+ ///
+ /// - Parameters:
+ /// - other: The vector to convert.
+ /// - rule: The round rule to use when converting elements of `other.` The
+ /// default is `.towardZero`.
@inlinable
init<Other>(
_ other: SIMD${n}<Other>,
@@ -118,6 +152,9 @@
}
public extension SIMD${n} where Scalar : BinaryFloatingPoint {
+ /// Creates a new vector from the given vector of integers.
+ ///
+ /// - Parameter other: The vector to convert.
@inlinable
init<Other>(_ other: SIMD${n}<Other>)
where Other : FixedWidthInteger {
@@ -125,6 +162,9 @@
for i in indices { self[i] = Scalar(other[i]) }
}
+ /// Creates a new vector from the given vector of floating-point values.
+ ///
+ /// - Parameter other: The vector to convert.
@inlinable
init<Other>(_ other: SIMD${n}<Other>)
where Other : BinaryFloatingPoint {
@@ -145,6 +185,7 @@
% for n in storagescalarCounts:
% bytes = n * self_type.bits / 8
+ /// Storage for a vector of ${spelledNumbers[n]} integers.
@_fixed_layout
@_alignment(${bytes if bytes <= 16 else 16})
public struct SIMD${n}Storage : SIMDStorage {
@@ -189,6 +230,7 @@
% for n in storagescalarCounts:
% bytes = n * bits / 8
+ /// Storage for a vector of ${spelledNumbers[n]} floating-point values.
@_fixed_layout
@_alignment(${bytes if bytes <= 16 else 16})
public struct SIMD${n}Storage : SIMDStorage {
diff --git a/stdlib/public/core/SequenceAlgorithms.swift b/stdlib/public/core/SequenceAlgorithms.swift
index b0a24e4..94834a0 100644
--- a/stdlib/public/core/SequenceAlgorithms.swift
+++ b/stdlib/public/core/SequenceAlgorithms.swift
@@ -581,7 +581,7 @@
/// predicate.
///
/// You can use this method to count the number of elements that pass a test.
- /// For example, this code finds the number of names that are fewer than
+ /// The following example finds the number of names that are fewer than
/// five characters long:
///
/// let names = ["Jacqueline", "Ian", "Amy", "Juan", "Soroush", "Tiffany"]
@@ -589,7 +589,7 @@
/// // shortNameCount == 3
///
/// To find the number of times a specific element appears in the sequence,
- /// use the equal-to operator (`==`) in the closure to test for a match.
+ /// use the equal to operator (`==`) in the closure to test for a match.
///
/// let birds = ["duck", "duck", "duck", "duck", "goose"]
/// let duckCount = birds.count(where: { $0 == "duck" })
diff --git a/stdlib/public/core/UnicodeScalar.swift b/stdlib/public/core/UnicodeScalar.swift
index 1f16ae2..18215e5 100644
--- a/stdlib/public/core/UnicodeScalar.swift
+++ b/stdlib/public/core/UnicodeScalar.swift
@@ -474,6 +474,9 @@
) rethrows -> Result {
let encodedScalar = UTF8.encode(self)!
var (codeUnits, utf8Count) = encodedScalar._bytes
+
+ // The first code unit is in the least significant byte of codeUnits.
+ codeUnits = codeUnits.littleEndian
return try Swift.withUnsafePointer(to: &codeUnits) {
return try $0.withMemoryRebound(to: UInt8.self, capacity: 4) {
return try body(UnsafeBufferPointer(start: $0, count: utf8Count))
diff --git a/stdlib/public/core/UnicodeScalarProperties.swift b/stdlib/public/core/UnicodeScalarProperties.swift
index ad4b8e1..21a6796 100644
--- a/stdlib/public/core/UnicodeScalarProperties.swift
+++ b/stdlib/public/core/UnicodeScalarProperties.swift
@@ -19,7 +19,6 @@
/// A value that provides access to properties of a Unicode scalar that are
/// defined by the Unicode standard.
-
public struct Properties {
@usableFromInline
internal var _scalar: Unicode.Scalar
@@ -34,8 +33,17 @@
}
}
- /// A value that provides access to properties of the Unicode scalar that are
- /// defined by the Unicode standard.
+ /// Properties of this scalar defined by the Unicode standard.
+ ///
+ /// Use this property to access the Unicode properties of a Unicode scalar
+ /// value. The following code tests whether a string contains any math
+ /// symbols:
+ ///
+ /// let question = "Which is larger, 3 * 3 * 3 or 10 + 10 + 10?"
+ /// let hasMathSymbols = question.unicodeScalars.contains(where: {
+ /// $0.properties.isMath
+ /// })
+ /// // hasMathSymbols == true
public var properties: Properties {
return Properties(self)
}
@@ -50,61 +58,61 @@
return __swift_stdlib_u_hasBinaryProperty(icuValue, property) != 0
}
- /// A Boolean property indicating whether the scalar is alphabetic.
+ /// A Boolean value indicating whether the scalar is alphabetic.
///
/// Alphabetic scalars are the primary units of alphabets and/or syllabaries.
///
- /// This property corresponds to the `Alphabetic` property in the
+ /// This property corresponds to the "Alphabetic" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isAlphabetic: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_ALPHABETIC)
}
- /// A Boolean property indicating whether the scalar is an ASCII character
+ /// A Boolean value indicating whether the scalar is an ASCII character
/// commonly used for the representation of hexadecimal numbers.
///
- /// The only scalars for which this property is true are:
+ /// The only scalars for which this property is `true` are:
///
/// * U+0030...U+0039: DIGIT ZERO...DIGIT NINE
/// * U+0041...U+0046: LATIN CAPITAL LETTER A...LATIN CAPITAL LETTER F
/// * U+0061...U+0066: LATIN SMALL LETTER A...LATIN SMALL LETTER F
///
- /// This property corresponds to the `ASCII_Hex_Digit` property in the
+ /// This property corresponds to the "ASCII_Hex_Digit" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isASCIIHexDigit: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_ASCII_HEX_DIGIT)
}
- /// A Boolean property indicating whether the scalar is a format control
+ /// A Boolean value indicating whether the scalar is a format control
/// character that has a specific function in the Unicode Bidrectional
/// Algorithm.
///
- /// This property corresponds to the `Bidi_Control` property in the
+ /// This property corresponds to the "Bidi_Control" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isBidiControl: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_BIDI_CONTROL)
}
- /// A Boolean property indicating whether the scalar is mirrored in
+ /// A Boolean value indicating whether the scalar is mirrored in
/// bidirectional text.
///
- /// This property corresponds to the `Bidi_Mirrored` property in the
+ /// This property corresponds to the "Bidi_Mirrored" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isBidiMirrored: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_BIDI_MIRRORED)
}
- /// A Boolean property indicating whether the scalar is a punctuation
+ /// A Boolean value indicating whether the scalar is a punctuation
/// symbol explicitly called out as a dash in the Unicode Standard or a
/// compatibility equivalent.
///
- /// This property corresponds to the `Dash` property in the
+ /// This property corresponds to the "Dash" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isDash: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_DASH)
}
- /// A Boolean property indicating whether the scalar is a default-ignorable
+ /// A Boolean value indicating whether the scalar is a default-ignorable
/// code point.
///
/// Default-ignorable code points are those that should be ignored by default
@@ -112,100 +120,103 @@
/// advance width in and of themselves, although they may affect the display,
/// positioning, or adornment of adjacent or surrounding characters.
///
- /// This property corresponds to the `Default_Ignorable_Code_Point` property
+ /// This property corresponds to the "Default_Ignorable_Code_Point" property
/// in the [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isDefaultIgnorableCodePoint: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_DEFAULT_IGNORABLE_CODE_POINT)
}
- /// A Boolean property indicating whether the scalar is deprecated.
+ /// A Boolean value indicating whether the scalar is deprecated.
///
/// Scalars are never removed from the Unicode Standard, but the usage of
/// deprecated scalars is strongly discouraged.
///
- /// This property corresponds to the `Deprecated` property in the
+ /// This property corresponds to the "Deprecated" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isDeprecated: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_DEPRECATED)
}
- /// A Boolean property indicating whether the scalar is a diacritic.
+ /// A Boolean value indicating whether the scalar is a diacritic.
///
/// Diacritics are scalars that linguistically modify the meaning of another
- /// scalar to which they apply. Scalars for which this property is true are
+ /// scalar to which they apply. Scalars for which this property is `true` are
/// frequently, but not always, combining marks or modifiers.
///
- /// This property corresponds to the `Diacritic` property in the
+ /// This property corresponds to the "Diacritic" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isDiacritic: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_DIACRITIC)
}
- /// A Boolean property indicating whether the scalar's principal function is
+ /// A Boolean value indicating whether the scalar's principal function is
/// to extend the value or shape of a preceding alphabetic scalar.
///
/// Typical extenders are length and iteration marks.
///
- /// This property corresponds to the `Extender` property in the
+ /// This property corresponds to the "Extender" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isExtender: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_EXTENDER)
}
- /// A Boolean property indicating whether the scalar is excluded from
+ /// A Boolean value indicating whether the scalar is excluded from
/// composition when performing Unicode normalization.
///
- /// This property corresponds to the `Full_Composition_Exclusion` property in
+ /// This property corresponds to the "Full_Composition_Exclusion" property in
/// the [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isFullCompositionExclusion: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_FULL_COMPOSITION_EXCLUSION)
}
- /// A Boolean property indicating whether the scalar is a grapheme base.
+ /// A Boolean value indicating whether the scalar is a grapheme base.
///
/// A grapheme base can be thought of as a space-occupying glyph above or
/// below which other non-spacing modifying glyphs can be applied. For
- /// example, when the character `é` is represented in NFD form, the grapheme
- /// base is "e" (U+0065 LATIN SMALL LETTER E) and it is followed by a single
- /// grapheme extender, U+0301 COMBINING ACUTE ACCENT.
+ /// example, when the character `é` is represented in its decomposed form,
+ /// the grapheme base is "e" (U+0065 LATIN SMALL LETTER E) and it is followed
+ /// by a single grapheme extender, U+0301 COMBINING ACUTE ACCENT.
///
- /// The set of scalars for which `isGraphemeBase` is true is disjoint by
- /// definition from the set for which `isGraphemeExtend` is true.
+ /// The set of scalars for which `isGraphemeBase` is `true` is disjoint by
+ /// definition from the set for which `isGraphemeExtend` is `true`.
///
- /// This property corresponds to the `Grapheme_Base` property in the
+ /// This property corresponds to the "Grapheme_Base" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isGraphemeBase: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_GRAPHEME_BASE)
}
- /// A Boolean property indicating whether the scalar is a grapheme extender.
+ /// A Boolean value indicating whether the scalar is a grapheme extender.
///
/// A grapheme extender can be thought of primarily as a non-spacing glyph
- /// that is applied above or below another glyph.
+ /// that is applied above or below another glyph. For example, when the
+ /// character `é` is represented in its decomposed form, the grapheme base is
+ /// "e" (U+0065 LATIN SMALL LETTER E) and it is followed by a single grapheme
+ /// extender, U+0301 COMBINING ACUTE ACCENT.
///
- /// The set of scalars for which `isGraphemeExtend` is true is disjoint by
- /// definition from the set for which `isGraphemeBase` is true.
+ /// The set of scalars for which `isGraphemeExtend` is `true` is disjoint by
+ /// definition from the set for which `isGraphemeBase` is `true`.
///
- /// This property corresponds to the `Grapheme_Extend` property in the
+ /// This property corresponds to the "Grapheme_Extend" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isGraphemeExtend: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_GRAPHEME_EXTEND)
}
- /// A Boolean property indicating whether the scalar is one that is commonly
+ /// A Boolean value indicating whether the scalar is one that is commonly
/// used for the representation of hexadecimal numbers or a compatibility
/// equivalent.
///
- /// This property is true for all scalars for which `isASCIIHexDigit` is true
- /// as well as for their CJK halfwidth and fullwidth variants.
+ /// This property is `true` for all scalars for which `isASCIIHexDigit` is
+ /// `true` as well as for their CJK halfwidth and fullwidth variants.
///
- /// This property corresponds to the `Hex_Digit` property in the
+ /// This property corresponds to the "Hex_Digit" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isHexDigit: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_HEX_DIGIT)
}
- /// A Boolean property indicating whether the scalar is one which is
+ /// A Boolean value indicating whether the scalar is one which is
/// recommended to be allowed to appear in a non-starting position in a
/// programming language identifier.
///
@@ -213,13 +224,13 @@
/// use `isXIDContinue` to check whether a scalar is a valid identifier
/// character.
///
- /// This property corresponds to the `ID_Continue` property in the
+ /// This property corresponds to the "ID_Continue" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isIDContinue: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_ID_CONTINUE)
}
- /// A Boolean property indicating whether the scalar is one which is
+ /// A Boolean value indicating whether the scalar is one which is
/// recommended to be allowed to appear in a starting position in a
/// programming language identifier.
///
@@ -227,13 +238,13 @@
/// use `isXIDStart` to check whether a scalar is a valid identifier
/// character.
///
- /// This property corresponds to the `ID_Start` property in the
+ /// This property corresponds to the "ID_Start" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isIDStart: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_ID_START)
}
- /// A Boolean property indicating whether the scalar is considered to be a
+ /// A Boolean value indicating whether the scalar is considered to be a
/// CJKV (Chinese, Japanese, Korean, and Vietnamese) or other siniform
/// (Chinese writing-related) ideograph.
///
@@ -241,13 +252,13 @@
/// not include characters of other logographic scripts such as Cuneiform or
/// Egyptian Hieroglyphs.
///
- /// This property corresponds to the `Ideographic` property in the
+ /// This property corresponds to the "Ideographic" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isIdeographic: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_IDEOGRAPHIC)
}
- /// A Boolean property indicating whether the scalar is an ideographic
+ /// A Boolean value indicating whether the scalar is an ideographic
/// description character that determines how the two ideographic characters
/// or ideographic description sequences that follow it are to be combined to
/// form a single character.
@@ -256,13 +267,13 @@
/// but advanced rendering engines may use them to approximate ideographs that
/// are otherwise unrepresentable.
///
- /// This property corresponds to the `IDS_Binary_Operator` property in the
+ /// This property corresponds to the "IDS_Binary_Operator" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isIDSBinaryOperator: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_IDS_BINARY_OPERATOR)
}
- /// A Boolean property indicating whether the scalar is an ideographic
+ /// A Boolean value indicating whether the scalar is an ideographic
/// description character that determines how the three ideographic characters
/// or ideographic description sequences that follow it are to be combined to
/// form a single character.
@@ -271,17 +282,17 @@
/// but advanced rendering engines may use them to approximate ideographs that
/// are otherwise unrepresentable.
///
- /// This property corresponds to the `IDS_Trinary_Operator` property in the
+ /// This property corresponds to the "IDS_Trinary_Operator" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isIDSTrinaryOperator: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_IDS_TRINARY_OPERATOR)
}
- /// A Boolean property indicating whether the scalar is a format control
+ /// A Boolean value indicating whether the scalar is a format control
/// character that has a specific function in controlling cursive joining and
/// ligation.
///
- /// There are two scalars for which this property is true:
+ /// There are two scalars for which this property is `true`:
///
/// * When U+200C ZERO WIDTH NON-JOINER is inserted between two characters, it
/// directs the rendering engine to render them separately/disconnected when
@@ -297,13 +308,13 @@
/// For example, the various "family" emoji are encoded as sequences of man,
/// woman, or child emoji that are interleaved with zero width joiners.
///
- /// This property corresponds to the `Join_Control` property in the
+ /// This property corresponds to the "Join_Control" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isJoinControl: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_JOIN_CONTROL)
}
- /// A Boolean property indicating whether the scalar requires special handling
+ /// A Boolean value indicating whether the scalar requires special handling
/// for operations involving ordering, such as sorting and searching.
///
/// This property applies to a small number of spacing vowel letters occurring
@@ -311,125 +322,125 @@
/// order display model. Such letters are stored in text ahead of
/// syllable-initial consonants.
///
- /// This property corresponds to the `Logical_Order_Exception` property in the
+ /// This property corresponds to the "Logical_Order_Exception" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isLogicalOrderException: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_LOGICAL_ORDER_EXCEPTION)
}
- /// A Boolean property indicating whether the scalar's letterform is
+ /// A Boolean value indicating whether the scalar's letterform is
/// considered lowercase.
///
- /// This property corresponds to the `Lowercase` property in the
+ /// This property corresponds to the "Lowercase" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isLowercase: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_LOWERCASE)
}
- /// A Boolean property indicating whether the scalar is one that naturally
+ /// A Boolean value indicating whether the scalar is one that naturally
/// appears in mathematical contexts.
///
- /// The set of scalars for which this property is true includes mathematical
+ /// The set of scalars for which this property is `true` includes mathematical
/// operators and symbols as well as specific Greek and Hebrew letter
/// variants that are categorized as symbols. Notably, it does _not_ contain
/// the standard digits or Latin/Greek letter blocks; instead, it contains the
/// mathematical Latin, Greek, and Arabic letters and numbers defined in the
/// Supplemental Multilingual Plane.
///
- /// This property corresponds to the `Math` property in the
+ /// This property corresponds to the "Math" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isMath: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_MATH)
}
- /// A Boolean property indicating whether the scalar is permanently reserved
+ /// A Boolean value indicating whether the scalar is permanently reserved
/// for internal use.
///
- /// This property corresponds to the `Noncharacter_Code_Point` property in the
+ /// This property corresponds to the "Noncharacter_Code_Point" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isNoncharacterCodePoint: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_NONCHARACTER_CODE_POINT)
}
- /// A Boolean property indicating whether the scalar is one that is used in
+ /// A Boolean value indicating whether the scalar is one that is used in
/// writing to surround quoted text.
///
- /// This property corresponds to the `Quotation_Mark` property in the
+ /// This property corresponds to the "Quotation_Mark" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isQuotationMark: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_QUOTATION_MARK)
}
- /// A Boolean property indicating whether the scalar is a radical component of
+ /// A Boolean value indicating whether the scalar is a radical component of
/// CJK characters, Tangut characters, or Yi syllables.
///
/// These scalars are often the components of ideographic description
/// sequences, as defined by the `isIDSBinaryOperator` and
/// `isIDSTrinaryOperator` properties.
///
- /// This property corresponds to the `Radical` property in the
+ /// This property corresponds to the "Radical" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isRadical: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_RADICAL)
}
- /// A Boolean property indicating whether the scalar has a "soft dot" that
+ /// A Boolean value indicating whether the scalar has a "soft dot" that
/// disappears when a diacritic is placed over the scalar.
///
/// For example, "i" is soft dotted because the dot disappears when adding an
/// accent mark, as in "í".
///
- /// This property corresponds to the `Soft_Dotted` property in the
+ /// This property corresponds to the "Soft_Dotted" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isSoftDotted: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_SOFT_DOTTED)
}
- /// A Boolean property indicating whether the scalar is a punctuation symbol
+ /// A Boolean value indicating whether the scalar is a punctuation symbol
/// that typically marks the end of a textual unit.
///
- /// This property corresponds to the `Terminal_Punctuation` property in the
+ /// This property corresponds to the "Terminal_Punctuation" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isTerminalPunctuation: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_TERMINAL_PUNCTUATION)
}
- /// A Boolean property indicating whether the scalar is one of the unified
+ /// A Boolean value indicating whether the scalar is one of the unified
/// CJK ideographs in the Unicode Standard.
///
/// This property is false for CJK punctuation and symbols, as well as for
/// compatibility ideographs (which canonically decompose to unified
/// ideographs).
///
- /// This property corresponds to the `Unified_Ideograph` property in the
+ /// This property corresponds to the "Unified_Ideograph" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isUnifiedIdeograph: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_UNIFIED_IDEOGRAPH)
}
- /// A Boolean property indicating whether the scalar's letterform is
+ /// A Boolean value indicating whether the scalar's letterform is
/// considered uppercase.
///
- /// This property corresponds to the `Uppercase` property in the
+ /// This property corresponds to the "Uppercase" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isUppercase: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_UPPERCASE)
}
- /// A Boolean property indicating whether the scalar is a whitespace
+ /// A Boolean value indicating whether the scalar is a whitespace
/// character.
///
- /// This property is true for scalars that are spaces, separator characters,
+ /// This property is `true` for scalars that are spaces, separator characters,
/// and other control characters that should be treated as whitespace for the
/// purposes of parsing text elements.
///
- /// This property corresponds to the `White_Space` property in the
+ /// This property corresponds to the "White_Space" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isWhitespace: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_WHITE_SPACE)
}
- /// A Boolean property indicating whether the scalar is one which is
+ /// A Boolean value indicating whether the scalar is one which is
/// recommended to be allowed to appear in a non-starting position in a
/// programming language identifier, with adjustments made for NFKC normalized
/// form.
@@ -438,13 +449,13 @@
/// under NFKC normalization by removing any scalars whose normalized form is
/// not of the form `[:ID_Continue:]*`.
///
- /// This property corresponds to the `XID_Continue` property in the
+ /// This property corresponds to the "XID_Continue" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isXIDContinue: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_XID_CONTINUE)
}
- /// A Boolean property indicating whether the scalar is one which is
+ /// A Boolean value indicating whether the scalar is one which is
/// recommended to be allowed to appear in a starting position in a
/// programming language identifier, with adjustments made for NFKC normalized
/// form.
@@ -453,132 +464,127 @@
/// NFKC normalization by removing any scalars whose normalized form is not of
/// the form `[:ID_Start:] [:ID_Continue:]*`.
///
- /// This property corresponds to the `XID_Start` property in the
+ /// This property corresponds to the "XID_Start" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isXIDStart: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_XID_START)
}
- /// A Boolean property indicating whether the scalar is a punctuation mark
+ /// A Boolean value indicating whether the scalar is a punctuation mark
/// that generally marks the end of a sentence.
///
- /// This property corresponds to the `Sentence_Terminal` property in the
+ /// This property corresponds to the "Sentence_Terminal" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isSentenceTerminal: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_S_TERM)
}
- /// A Boolean property indicating whether the scalar is a variation selector.
+ /// A Boolean value indicating whether the scalar is a variation selector.
///
/// Variation selectors allow rendering engines that support them to choose
/// different glyphs to display for a particular code point.
///
- /// This property corresponds to the `Variation_Selector` property in the
+ /// This property corresponds to the "Variation_Selector" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isVariationSelector: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_VARIATION_SELECTOR)
}
- /// A Boolean property indicating whether the scalar is recommended to have
+ /// A Boolean value indicating whether the scalar is recommended to have
/// syntactic usage in patterns represented in source code.
///
- /// This property corresponds to the `Pattern_Syntax` property in the
+ /// This property corresponds to the "Pattern_Syntax" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isPatternSyntax: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_PATTERN_SYNTAX)
}
- /// A Boolean property indicating whether the scalar is recommended to be
+ /// A Boolean value indicating whether the scalar is recommended to be
/// treated as whitespace when parsing patterns represented in source code.
///
- /// This property corresponds to the `Pattern_White_Space` property in the
+ /// This property corresponds to the "Pattern_White_Space" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isPatternWhitespace: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_PATTERN_WHITE_SPACE)
}
- /// A Boolean property indicating whether the scalar is considered to be
+ /// A Boolean value indicating whether the scalar is considered to be
/// either lowercase, uppercase, or titlecase.
///
- /// Though similar in name, this property is _not_ equivalent to
- /// `changesWhenCaseMapped`. The set of scalars for which `isCased` is true is
- /// a superset of those for which `changesWhenCaseMapped` is true. An example
- /// of scalars that only have `isCased` as true are the Latin small capitals
- /// that are used by the International Phonetic Alphabet. These letters have a
- /// case but do not change when they are mapped to any of the other cases.
+ /// Though similar in name, this property is *not* equivalent to
+ /// `changesWhenCaseMapped`. The set of scalars for which `isCased` is `true`
+ /// is a superset of those for which `changesWhenCaseMapped` is `true`. For
+ /// example, the Latin small capitals that are used by the International
+ /// Phonetic Alphabet have a case, but do not change when they are mapped to
+ /// any of the other cases.
///
- /// This property corresponds to the `Cased` property in the
+ /// This property corresponds to the "Cased" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isCased: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_CASED)
}
- /// A Boolean property indicating whether the scalar is ignored for casing
+ /// A Boolean value indicating whether the scalar is ignored for casing
/// purposes.
///
- /// This property corresponds to the `Case_Ignorable` property in the
+ /// This property corresponds to the "Case_Ignorable" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var isCaseIgnorable: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_CASE_IGNORABLE)
}
- /// A Boolean property indicating whether the scalar's normalized form differs
+ /// A Boolean value indicating whether the scalar's normalized form differs
/// from the `lowercaseMapping` of each constituent scalar.
///
- /// This property corresponds to the `Changes_When_Lowercased` property in the
+ /// This property corresponds to the "Changes_When_Lowercased" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var changesWhenLowercased: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_CHANGES_WHEN_LOWERCASED)
}
- /// A Boolean property indicating whether the scalar's normalized form differs
+ /// A Boolean value indicating whether the scalar's normalized form differs
/// from the `uppercaseMapping` of each constituent scalar.
///
- /// This property corresponds to the `Changes_When_Uppercased` property in the
+ /// This property corresponds to the "Changes_When_Uppercased" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var changesWhenUppercased: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_CHANGES_WHEN_UPPERCASED)
}
- /// A Boolean property indicating whether the scalar's normalized form differs
+ /// A Boolean value indicating whether the scalar's normalized form differs
/// from the `titlecaseMapping` of each constituent scalar.
///
- /// This property corresponds to the `Changes_When_Titlecased` property in the
+ /// This property corresponds to the "Changes_When_Titlecased" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var changesWhenTitlecased: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_CHANGES_WHEN_TITLECASED)
}
- /// A Boolean property indicating whether the scalar's normalized form differs
+ /// A Boolean value indicating whether the scalar's normalized form differs
/// from the case-fold mapping of each constituent scalar.
///
- /// This property corresponds to the `Changes_When_Casefolded` property in the
+ /// This property corresponds to the "Changes_When_Casefolded" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var changesWhenCaseFolded: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_CHANGES_WHEN_CASEFOLDED)
}
- /// A Boolean property indicating whether the scalar may change when it
+ /// A Boolean value indicating whether the scalar may change when it
/// undergoes case mapping.
///
- /// For any scalar `s`, it holds by definition that
+ /// This property is `true` whenever one or more of `changesWhenLowercased`,
+ /// `changesWhenUppercased`, or `changesWhenTitlecased` are `true`.
///
- /// ```
- /// s.changesWhenCaseMapped = s.changesWhenLowercased ||
- /// s.changesWhenUppercased ||
- /// s.changesWhenTitlecased
- /// ```
- ///
- /// This property corresponds to the `Changes_When_Casemapped` property in the
+ /// This property corresponds to the "Changes_When_Casemapped" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var changesWhenCaseMapped: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_CHANGES_WHEN_CASEMAPPED)
}
- /// A Boolean property indicating whether the scalar is one that is not
+ /// A Boolean value indicating whether the scalar is one that is not
/// identical to its NFKC case-fold mapping.
///
- /// This property corresponds to the `Changes_When_NFKC_Casefolded` property
+ /// This property corresponds to the "Changes_When_NFKC_Casefolded" property
/// in the [Unicode Standard](http://www.unicode.org/versions/latest/).
public var changesWhenNFKCCaseFolded: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_CHANGES_WHEN_NFKC_CASEFOLDED)
@@ -590,7 +596,7 @@
// non-Darwin platforms for now; bundling ICU with the toolchain would resolve
// this and other inconsistencies (https://bugs.swift.org/browse/SR-6076).
- /// A Boolean property indicating whether the scalar has an emoji
+ /// A Boolean value indicating whether the scalar has an emoji
/// presentation, whether or not it is the default.
///
/// This property is true for scalars that are rendered as emoji by default
@@ -598,18 +604,13 @@
/// by U+FE0F VARIATION SELECTOR-16. This includes some scalars that are not
/// typically considered to be emoji:
///
- /// ```
- /// let sunglasses: Unicode.Scalar = "😎"
- /// let dollar: Unicode.Scalar = "$"
- /// let zero: Unicode.Scalar = "0"
- ///
- /// print(sunglasses.isEmoji)
- /// // Prints "true"
- /// print(dollar.isEmoji)
- /// // Prints "false"
- /// print(zero.isEmoji)
- /// // Prints "true"
- /// ```
+ /// let scalars: [Unicode.Scalar] = ["😎", "$", "0"]
+ /// for s in scalars {
+ /// print(s, "-->", s.isEmoji)
+ /// }
+ /// // 😎 --> true
+ /// // $ --> false
+ /// // 0 --> true
///
/// The final result is true because the ASCII digits have non-default emoji
/// presentations; some platforms render these with an alternate appearance.
@@ -622,48 +623,48 @@
/// determine whether it is followed by a variation selector that would modify
/// the presentation.
///
- /// This property corresponds to the `Emoji` property in the
+ /// This property corresponds to the "Emoji" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
@available(macOS 10.12.2, iOS 10.2, tvOS 10.1, watchOS 3.1.1, *)
public var isEmoji: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_EMOJI)
}
- /// A Boolean property indicating whether the scalar is one that should be
+ /// A Boolean value indicating whether the scalar is one that should be
/// rendered with an emoji presentation, rather than a text presentation, by
/// default.
///
- /// Scalars that have emoji presentation by default can be followed by
+ /// Scalars that have default to emoji presentation can be followed by
/// U+FE0E VARIATION SELECTOR-15 to request the text presentation of the
/// scalar instead. Likewise, scalars that default to text presentation can
/// be followed by U+FE0F VARIATION SELECTOR-16 to request the emoji
/// presentation.
///
- /// This property corresponds to the `Emoji_Presentation` property in the
+ /// This property corresponds to the "Emoji_Presentation" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
@available(macOS 10.12.2, iOS 10.2, tvOS 10.1, watchOS 3.1.1, *)
public var isEmojiPresentation: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_EMOJI_PRESENTATION)
}
- /// A Boolean property indicating whether the scalar is one that can modify
+ /// A Boolean value indicating whether the scalar is one that can modify
/// a base emoji that precedes it.
///
/// The Fitzpatrick skin types are examples of emoji modifiers; they change
/// the appearance of the preceding emoji base (that is, a scalar for which
/// `isEmojiModifierBase` is true) by rendering it with a different skin tone.
///
- /// This property corresponds to the `Emoji_Modifier` property in the
+ /// This property corresponds to the "Emoji_Modifier" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
@available(macOS 10.12.2, iOS 10.2, tvOS 10.1, watchOS 3.1.1, *)
public var isEmojiModifier: Bool {
return _hasBinaryProperty(__swift_stdlib_UCHAR_EMOJI_MODIFIER)
}
- /// A Boolean property indicating whether the scalar is one whose appearance
+ /// A Boolean value indicating whether the scalar is one whose appearance
/// can be changed by an emoji modifier that follows it.
///
- /// This property corresponds to the `Emoji_Modifier_Base` property in the
+ /// This property corresponds to the "Emoji_Modifier_Base" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
@available(macOS 10.12.2, iOS 10.2, tvOS 10.1, watchOS 3.1.1, *)
public var isEmojiModifierBase: Bool {
@@ -725,7 +726,7 @@
/// WITH DOT ABOVE) becomes two scalars (U+0069 LATIN SMALL LETTER I, U+0307
/// COMBINING DOT ABOVE) when converted to lowercase.
///
- /// This property corresponds to the `Lowercase_Mapping` property in the
+ /// This property corresponds to the "Lowercase_Mapping" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var lowercaseMapping: String {
return _applyMapping(__swift_stdlib_u_strToLower)
@@ -739,7 +740,7 @@
/// becomes "Fi" (U+0046 LATIN CAPITAL LETTER F, U+0069 LATIN SMALL LETTER I)
/// when converted to titlecase.
///
- /// This property corresponds to the `Titlecase_Mapping` property in the
+ /// This property corresponds to the "Titlecase_Mapping" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var titlecaseMapping: String {
return _applyMapping { ptr, cap, src, len, locale, err in
@@ -755,7 +756,7 @@
/// SHARP S) becomes "SS" (U+0053 LATIN CAPITAL LETTER S, U+0053 LATIN CAPITAL
/// LETTER S) when converted to uppercase.
///
- /// This property corresponds to the `Uppercase_Mapping` property in the
+ /// This property corresponds to the "Uppercase_Mapping" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var uppercaseMapping: String {
return _applyMapping(__swift_stdlib_u_strToUpper)
@@ -764,7 +765,7 @@
extension Unicode {
- /// A version of the Unicode Standard represented by its `major.minor`
+ /// A version of the Unicode Standard represented by its major and minor
/// components.
public typealias Version = (major: Int, minor: Int)
}
@@ -774,9 +775,9 @@
/// The earliest version of the Unicode Standard in which the scalar was
/// assigned.
///
- /// This value will be nil for code points that have not yet been assigned.
+ /// This value is `nil` for code points that have not yet been assigned.
///
- /// This property corresponds to the `Age` property in the
+ /// This property corresponds to the "Age" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var age: Unicode.Version? {
var versionInfo: __swift_stdlib_UVersionInfo = (0, 0, 0, 0)
@@ -1074,7 +1075,7 @@
/// The general category (most usual classification) of the scalar.
///
- /// This property corresponds to the `General_Category` property in the
+ /// This property corresponds to the "General_Category" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var generalCategory: Unicode.GeneralCategory {
let rawValue = __swift_stdlib_UCharCategory(
@@ -1117,15 +1118,16 @@
/// The published name of the scalar.
///
/// Some scalars, such as control characters, do not have a value for this
- /// property in the UCD. For such scalars, this property will be nil.
+ /// property in the Unicode Character Database. For such scalars, this
+ /// property is `nil`.
///
- /// This property corresponds to the `Name` property in the
+ /// This property corresponds to the "Name" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var name: String? {
return _scalarName(__swift_stdlib_U_UNICODE_CHAR_NAME)
}
- /// The normative formal alias of the scalar, or nil if it has no alias.
+ /// The normative formal alias of the scalar.
///
/// The name of a scalar is immutable and never changed in future versions of
/// the Unicode Standard. The `nameAlias` property is provided to issue
@@ -1134,7 +1136,9 @@
/// (note that "BRACKET" is misspelled). The `nameAlias` property then
/// contains the corrected name.
///
- /// This property corresponds to the `Name_Alias` property in the
+ /// If a scalar has no alias, this property is `nil`.
+ ///
+ /// This property corresponds to the "Name_Alias" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var nameAlias: String? {
return _scalarName(__swift_stdlib_U_CHAR_NAME_ALIAS)
@@ -1159,10 +1163,10 @@
/// `"\u{0041}\u{0316}\u{0301}"`, so two strings that differ only by the
/// ordering of those scalars would compare as equal:
///
- /// ```
- /// print("\u{0041}\u{0316}\u{0301}" == "\u{0041}\u{0301}\u{0316}")
- /// // Prints "true"
- /// ```
+ /// let aboveBeforeBelow = "\u{0041}\u{0301}\u{0316}"
+ /// let belowBeforeAbove = "\u{0041}\u{0316}\u{0301}"
+ /// print(aboveBeforeBelow == belowBeforeAbove)
+ /// // Prints "true"
///
/// Named and Unnamed Combining Classes
/// ===================================
@@ -1172,15 +1176,13 @@
/// symbolic names to a subset of these combining classes.
///
/// The `CanonicalCombiningClass` type conforms to `RawRepresentable` with a
- /// raw value of type `UInt8`. Instances of the type can be created from the
- /// actual numeric value using the `init(rawValue:)` initializer, and
- /// combining classes with symbolic names can also be referenced using the
- /// static members that share those names.
+ /// raw value of type `UInt8`. You can create instances of the type by using
+ /// the static members named after the symbolic names, or by using the
+ /// `init(rawValue:)` initializer.
///
- /// ```
- /// print(Unicode.CanonicalCombiningClass(rawValue: 1) == .overlay)
- /// // Prints "true"
- /// ```
+ /// let overlayClass = Unicode.CanonicalCombiningClass(rawValue: 1)
+ /// let overlayClassIsOverlay = overlayClass == .overlay
+ /// // overlayClassIsOverlay == true
public struct CanonicalCombiningClass:
Comparable, Hashable, RawRepresentable
{
@@ -1286,7 +1288,7 @@
/// The canonical combining class of the scalar.
///
- /// This property corresponds to the `Canonical_Combining_Class` property in
+ /// This property corresponds to the "Canonical_Combining_Class" property in
/// the [Unicode Standard](http://www.unicode.org/versions/latest/).
public var canonicalCombiningClass: Unicode.CanonicalCombiningClass {
let rawValue = UInt8(__swift_stdlib_u_getIntPropertyValue(
@@ -1308,32 +1310,35 @@
/// from incorrectly interpreting them as numbers in non-numeric contexts.
public enum NumericType {
- /// Digits that are commonly understood to form base-10 numbers.
+ /// A digit that is commonly understood to form base-10 numbers.
///
/// Specifically, scalars have this numeric type if they occupy a contiguous
/// range of code points representing numeric values `0...9`.
case decimal
- /// Decimal digits that otherwise do not meet the requirements of numeric
- /// type `decimal`.
+ /// A digit that does not meet the requirements of the `decimal` numeric
+ /// type.
///
/// Scalars with this numeric type are often those that represent a decimal
- /// digit but would not typically be used to write a base-10 number, such as
- /// "④" (U+2463 CIRCLED DIGIT FOUR).
+ /// digit but would not typically be used to write a base-10 number, such
+ /// as "④" (U+2463 CIRCLED DIGIT FOUR).
///
- /// In practice, the distinction between `digit` and `numeric` has not
- /// proven to be valuable. As of Unicode 6.3, any new scalars that represent
- /// numbers but do not meet the requirements of `decimal` will have numeric
- /// type `numeric`, and programs can treat `digit` and `numeric`
- /// equivalently.
+ /// As of Unicode 6.3, any new scalars that represent numbers but do not
+ /// meet the requirements of `decimal` will have numeric type `numeric`,
+ /// and programs can treat `digit` and `numeric` equivalently.
case digit
- /// Numbers that are not decimal digits.
+ /// A digit that does not meet the requirements of the `decimal` numeric
+ /// type or a non-digit numeric value.
///
- /// This numeric type includes fractions such as "⅕" (U+2155 VULGAR FRACITON
- /// ONE FIFTH), numerical CJK ideographs like "兆" (U+5146 CJK UNIFIED
- /// IDEOGRAPH-5146), and other scalars that are not decimal digits used
- /// positionally in the writing of base-10 numbers.
+ /// This numeric type includes fractions such as "⅕" (U+2155 VULGAR
+ /// FRACITON ONE FIFTH), numerical CJK ideographs like "兆" (U+5146 CJK
+ /// UNIFIED IDEOGRAPH-5146), and other scalars that are not decimal digits
+ /// used positionally in the writing of base-10 numbers.
+ ///
+ /// As of Unicode 6.3, any new scalars that represent numbers but do not
+ /// meet the requirements of `decimal` will have numeric type `numeric`,
+ /// and programs can treat `digit` and `numeric` equivalently.
case numeric
internal init?(rawValue: __swift_stdlib_UNumericType) {
@@ -1353,21 +1358,19 @@
/// The numeric type of the scalar.
///
- /// The value of this property is nil for scalars that do not represent a
- /// number.
+ /// For scalars that represent a number, `numericType` is the numeric type
+ /// of the scalar. For all other scalars, this property is `nil`.
///
- /// ```
- /// print("X", ("X" as Unicode.Scalar).properties.numericType ?? "nil")
- /// // Prints "X nil"
- /// print("4", ("4" as Unicode.Scalar).properties.numericType ?? "nil")
- /// // Prints "4 decimal"
- /// print("\u{2463}", ("\u{2463}" as Unicode.Scalar).properties.numericType ?? "nil")
- /// // Prints "④ digit"
- /// print("\u{2155}", ("\u{2155}" as Unicode.Scalar).properties.numericType ?? "nil")
- /// // Prints "⅕ numeric"
- /// ```
+ /// let scalars: [Unicode.Scalar] = ["4", "④", "⅕", "X"]
+ /// for scalar in scalars {
+ /// print(scalar, "-->", scalar.properties.numericType)
+ /// }
+ /// // 4 --> decimal
+ /// // ④ --> digit
+ /// // ⅕ --> numeric
+ /// // X --> nil
///
- /// This property corresponds to the `Numeric_Type` property in the
+ /// This property corresponds to the "Numeric_Type" property in the
/// [Unicode Standard](http://www.unicode.org/versions/latest/).
public var numericType: Unicode.NumericType? {
let rawValue = __swift_stdlib_UNumericType(
@@ -1379,25 +1382,20 @@
/// The numeric value of the scalar.
///
- /// The value of this property is nil for scalars that do not represent a
- /// number.
+ /// For scalars that represent a numeric value, `numericValue` is the whole
+ /// or fractional value. For all other scalars, this property is `nil`.
///
- /// The numeric value of a scalar is represented as a `Double` because some
- /// scalars represent fractions:
+ /// let scalars: [Unicode.Scalar] = ["4", "④", "⅕", "X"]
+ /// for scalar in scalars {
+ /// print(scalar, "-->", scalar.properties.numericValue)
+ /// }
+ /// // 4 --> 4.0
+ /// // ④ --> 4.0
+ /// // ⅕ --> 0.2
+ /// // X --> nil
///
- /// ```
- /// print("X", ("X" as Unicode.Scalar).properties.numericValue ?? "nil")
- /// // Prints "X nil"
- /// print("4", ("4" as Unicode.Scalar).properties.numericValue ?? "nil")
- /// // Prints "4 4.0"
- /// print("\u{2463}", ("\u{2463}" as Unicode.Scalar).properties.numericValue ?? "nil")
- /// // Prints "④ 4.0"
- /// print("\u{2155}", ("\u{2155}" as Unicode.Scalar).properties.numericValue ?? "nil")
- /// // Prints "⅕ 0.2"
- /// ```
- ///
- /// This property corresponds to the `Numeric_Value` property in the
- /// [Unicode Standard](http://www.unicode.org/versions/latest/).
+ /// This property corresponds to the "Numeric_Value" property in the [Unicode
+ /// Standard](http://www.unicode.org/versions/latest/).
public var numericValue: Double? {
let icuNoNumericValue: Double = -123456789
let result = __swift_stdlib_u_getNumericValue(icuValue)
diff --git a/stdlib/public/core/UnsafeBufferPointer.swift.gyb b/stdlib/public/core/UnsafeBufferPointer.swift.gyb
index 6b882ad..2648f47 100644
--- a/stdlib/public/core/UnsafeBufferPointer.swift.gyb
+++ b/stdlib/public/core/UnsafeBufferPointer.swift.gyb
@@ -567,7 +567,22 @@
public static func allocate(capacity count: Int)
-> UnsafeMutableBufferPointer<Element> {
let size = MemoryLayout<Element>.stride * count
- let raw = Builtin.allocRaw(size._builtinWordValue, Builtin.alignof(Element.self))
+ // For any alignment <= _minAllocationAlignment, force alignment = 0.
+ // This forces the runtime's "aligned" allocation path so that
+ // deallocation does not require the original alignment.
+ //
+ // The runtime guarantees:
+ //
+ // align == 0 || align > _minAllocationAlignment:
+ // Runtime uses "aligned allocation".
+ //
+ // 0 < align <= _minAllocationAlignment:
+ // Runtime may use either malloc or "aligned allocation".
+ var align = Builtin.alignof(Element.self)
+ if Int(align) <= _minAllocationAlignment() {
+ align = (0)._builtinWordValue
+ }
+ let raw = Builtin.allocRaw(size._builtinWordValue, align)
Builtin.bindMemory(raw, count._builtinWordValue, Element.self)
return UnsafeMutableBufferPointer(
start: UnsafeMutablePointer(raw), count: count)
diff --git a/stdlib/public/core/UnsafePointer.swift b/stdlib/public/core/UnsafePointer.swift
index 0103779..0735a38 100644
--- a/stdlib/public/core/UnsafePointer.swift
+++ b/stdlib/public/core/UnsafePointer.swift
@@ -225,7 +225,11 @@
/// block. The memory must not be initialized or `Pointee` must be a trivial type.
@inlinable
public func deallocate() {
- Builtin.deallocRaw(_rawValue, (-1)._builtinWordValue, (-1)._builtinWordValue)
+ // Passing zero alignment to the runtime forces "aligned
+ // deallocation". Since allocation via `UnsafeMutable[Raw][Buffer]Pointer`
+ // always uses the "aligned allocation" path, this ensures that the
+ // runtime's allocation and deallocation paths are compatible.
+ Builtin.deallocRaw(_rawValue, (-1)._builtinWordValue, (0)._builtinWordValue)
}
/// Accesses the instance referenced by this pointer.
@@ -568,8 +572,22 @@
public static func allocate(capacity count: Int)
-> UnsafeMutablePointer<Pointee> {
let size = MemoryLayout<Pointee>.stride * count
- let rawPtr =
- Builtin.allocRaw(size._builtinWordValue, Builtin.alignof(Pointee.self))
+ // For any alignment <= _minAllocationAlignment, force alignment = 0.
+ // This forces the runtime's "aligned" allocation path so that
+ // deallocation does not require the original alignment.
+ //
+ // The runtime guarantees:
+ //
+ // align == 0 || align > _minAllocationAlignment:
+ // Runtime uses "aligned allocation".
+ //
+ // 0 < align <= _minAllocationAlignment:
+ // Runtime may use either malloc or "aligned allocation".
+ var align = Builtin.alignof(Pointee.self)
+ if Int(align) <= _minAllocationAlignment() {
+ align = (0)._builtinWordValue
+ }
+ let rawPtr = Builtin.allocRaw(size._builtinWordValue, align)
Builtin.bindMemory(rawPtr, count._builtinWordValue, Pointee.self)
return UnsafeMutablePointer(rawPtr)
}
@@ -580,8 +598,11 @@
/// block. The memory must not be initialized or `Pointee` must be a trivial type.
@inlinable
public func deallocate() {
- Builtin.deallocRaw(_rawValue, (-1)._builtinWordValue,
- Builtin.alignof(Pointee.self))
+ // Passing zero alignment to the runtime forces "aligned
+ // deallocation". Since allocation via `UnsafeMutable[Raw][Buffer]Pointer`
+ // always uses the "aligned allocation" path, this ensures that the
+ // runtime's allocation and deallocation paths are compatible.
+ Builtin.deallocRaw(_rawValue, (-1)._builtinWordValue, (0)._builtinWordValue)
}
/// Accesses the instance referenced by this pointer.
diff --git a/stdlib/public/core/UnsafeRawPointer.swift b/stdlib/public/core/UnsafeRawPointer.swift
index 73cad75..3b23b08 100644
--- a/stdlib/public/core/UnsafeRawPointer.swift
+++ b/stdlib/public/core/UnsafeRawPointer.swift
@@ -241,7 +241,11 @@
/// trivial type.
@inlinable
public func deallocate() {
- Builtin.deallocRaw(_rawValue, (-1)._builtinWordValue, (-1)._builtinWordValue)
+ // Passing zero alignment to the runtime forces "aligned
+ // deallocation". Since allocation via `UnsafeMutable[Raw][Buffer]Pointer`
+ // always uses the "aligned allocation" path, this ensures that the
+ // runtime's allocation and deallocation paths are compatible.
+ Builtin.deallocRaw(_rawValue, (-1)._builtinWordValue, (0)._builtinWordValue)
}
/// Binds the memory to the specified type and returns a typed pointer to the
@@ -577,6 +581,21 @@
public static func allocate(
byteCount: Int, alignment: Int
) -> UnsafeMutableRawPointer {
+ // For any alignment <= _minAllocationAlignment, force alignment = 0.
+ // This forces the runtime's "aligned" allocation path so that
+ // deallocation does not require the original alignment.
+ //
+ // The runtime guarantees:
+ //
+ // align == 0 || align > _minAllocationAlignment:
+ // Runtime uses "aligned allocation".
+ //
+ // 0 < align <= _minAllocationAlignment:
+ // Runtime may use either malloc or "aligned allocation".
+ var alignment = alignment
+ if alignment <= _minAllocationAlignment() {
+ alignment = 0
+ }
return UnsafeMutableRawPointer(Builtin.allocRaw(
byteCount._builtinWordValue, alignment._builtinWordValue))
}
@@ -587,7 +606,11 @@
/// trivial type.
@inlinable
public func deallocate() {
- Builtin.deallocRaw(_rawValue, (-1)._builtinWordValue, (-1)._builtinWordValue)
+ // Passing zero alignment to the runtime forces "aligned
+ // deallocation". Since allocation via `UnsafeMutable[Raw][Buffer]Pointer`
+ // always uses the "aligned allocation" path, this ensures that the
+ // runtime's allocation and deallocation paths are compatible.
+ Builtin.deallocRaw(_rawValue, (-1)._builtinWordValue, (0)._builtinWordValue)
}
/// Binds the memory to the specified type and returns a typed pointer to the
diff --git a/stdlib/public/runtime/Heap.cpp b/stdlib/public/runtime/Heap.cpp
index 8f7258a..46e133a 100644
--- a/stdlib/public/runtime/Heap.cpp
+++ b/stdlib/public/runtime/Heap.cpp
@@ -18,6 +18,7 @@
#include "swift/Runtime/Heap.h"
#include "Private.h"
#include "swift/Runtime/Debug.h"
+#include "../SwiftShims/RuntimeShims.h"
#include <algorithm>
#include <stdlib.h>
@@ -48,19 +49,61 @@
#endif
+// This assert ensures that manually allocated memory always uses the
+// AlignedAlloc path. The stdlib will use "default" alignment for any user
+// requested alignment less than or equal to _swift_MinAllocationAlignment. The
+// runtime must ensure that any alignment > _swift_MinAllocationAlignment also
+// uses the "aligned" deallocation path.
+static_assert(_swift_MinAllocationAlignment > MALLOC_ALIGN_MASK,
+ "Swift's default alignment must exceed platform malloc mask.");
-
+// When alignMask == ~(size_t(0)), allocation uses the "default"
+// _swift_MinAllocationAlignment. This is different than calling swift_slowAlloc
+// with `alignMask == _swift_MinAllocationAlignment - 1` because it forces
+// the use of AlignedAlloc. This allows manually allocated to memory to always
+// be deallocated with AlignedFree without knowledge of its original allocation
+// alignment.
+//
+// For alignMask > (_minAllocationAlignment-1)
+// i.e. alignment == 0 || alignment > _minAllocationAlignment:
+// The runtime must use AlignedAlloc, and the standard library must
+// deallocate using an alignment that meets the same condition.
+//
+// For alignMask <= (_minAllocationAlignment-1)
+// i.e. 0 < alignment <= _minAllocationAlignment:
+// The runtime may use either malloc or AlignedAlloc, and the standard library
+// must deallocate using an identical alignment.
void *swift::swift_slowAlloc(size_t size, size_t alignMask) {
void *p;
+ // This check also forces "default" alignment to use AlignedAlloc.
if (alignMask <= MALLOC_ALIGN_MASK) {
p = malloc(size);
} else {
- p = AlignedAlloc(size, alignMask + 1);
+ size_t alignment = (alignMask == ~(size_t(0)))
+ ? _swift_MinAllocationAlignment
+ : alignMask + 1;
+ p = AlignedAlloc(size, alignment);
}
if (!p) swift::crash("Could not allocate memory.");
return p;
}
+// Unknown alignment is specified by passing alignMask == ~(size_t(0)), forcing
+// the AlignedFree deallocation path for unknown alignment. The memory
+// deallocated with unknown alignment must have been allocated with either
+// "default" alignment, or alignment > _swift_MinAllocationAlignment, to
+// guarantee that it was allocated with AlignedAlloc.
+//
+// The standard library assumes the following behavior:
+//
+// For alignMask > (_minAllocationAlignment-1)
+// i.e. alignment == 0 || alignment > _minAllocationAlignment:
+// The runtime must use AlignedFree.
+//
+// For alignMask <= (_minAllocationAlignment-1)
+// i.e. 0 < alignment <= _minAllocationAlignment:
+// The runtime may use either `free` or AlignedFree as long as it is
+// consistent with allocation with the same alignment.
void swift::swift_slowDealloc(void *ptr, size_t bytes, size_t alignMask) {
if (alignMask <= MALLOC_ALIGN_MASK) {
free(ptr);
diff --git a/test/Interpreter/builtin_bridge_object.swift b/test/Interpreter/builtin_bridge_object.swift
index a49ed02..4b7ad1a 100644
--- a/test/Interpreter/builtin_bridge_object.swift
+++ b/test/Interpreter/builtin_bridge_object.swift
@@ -30,7 +30,7 @@
#elseif arch(arm64)
// We have ObjC tagged pointers in the highest bit
-let NATIVE_SPARE_BITS: UInt = 0x7F00_0000_0000_0007
+let NATIVE_SPARE_BITS: UInt = 0x7000_0000_0000_0007
let OBJC_TAGGED_POINTER_BITS: UInt = 0x8000_0000_0000_0000
#elseif arch(powerpc64) || arch(powerpc64le)
diff --git a/test/ParseableInterface/fixed-layout-property-initializers.swift b/test/ParseableInterface/fixed-layout-property-initializers.swift
index 099a214..08e6c87 100644
--- a/test/ParseableInterface/fixed-layout-property-initializers.swift
+++ b/test/ParseableInterface/fixed-layout-property-initializers.swift
@@ -1,37 +1,38 @@
// RUN: %empty-directory(%t)
// RUN: %target-swift-frontend -typecheck -emit-parseable-module-interface-path %t.swiftinterface %s
-// RUN: %FileCheck %s --check-prefix FROMSOURCE --check-prefix CHECK < %t.swiftinterface
+// RUN: %FileCheck %s --check-prefix FROMSOURCE --check-prefix NONRESILIENT --check-prefix COMMON < %t.swiftinterface
// RUN: %target-swift-frontend -typecheck -emit-parseable-module-interface-path %t-resilient.swiftinterface -enable-resilience %s
-// RUN: %FileCheck %s --check-prefix FROMSOURCE --check-prefix CHECK < %t-resilient.swiftinterface
+// RUN: %FileCheck %s --check-prefix FROMSOURCE --check-prefix RESILIENT --check-prefix COMMON < %t-resilient.swiftinterface
// RUN: %target-swift-frontend -emit-module -o %t/Test.swiftmodule %t.swiftinterface -disable-objc-attr-requires-foundation-module
-// RUN: %target-swift-frontend -emit-module -o /dev/null -merge-modules %t/Test.swiftmodule -module-name Test -emit-parseable-module-interface-path - | %FileCheck %s --check-prefix FROMMODULE --check-prefix CHECK
+// RUN: %target-swift-frontend -emit-module -o /dev/null -merge-modules %t/Test.swiftmodule -module-name Test -emit-parseable-module-interface-path - | %FileCheck %s --check-prefix FROMMODULE --check-prefix NONRESILIENT --check-prefix COMMON
// RUN: %target-swift-frontend -emit-module -o %t/TestResilient.swiftmodule -enable-resilience %t-resilient.swiftinterface -disable-objc-attr-requires-foundation-module
-// RUN: %target-swift-frontend -emit-module -o /dev/null -merge-modules %t/TestResilient.swiftmodule -module-name TestResilient -enable-resilience -emit-parseable-module-interface-path - | %FileCheck %s --check-prefix FROMMODULE --check-prefix CHECK
+// RUN: %target-swift-frontend -emit-module -o /dev/null -merge-modules %t/TestResilient.swiftmodule -module-name TestResilient -enable-resilience -emit-parseable-module-interface-path - | %FileCheck %s --check-prefix FROMMODULE --check-prefix RESILIENT --check-prefix COMMON
-// CHECK: @_fixed_layout public struct MyStruct {
+// COMMON: @_fixed_layout public struct MyStruct {
@_fixed_layout
public struct MyStruct {
- // CHECK: public var publicVar: [[BOOL:(Swift\.)?Bool]] = false
+ // COMMON: public var publicVar: [[BOOL:(Swift\.)?Bool]] = false
public var publicVar: Bool = false
- // CHECK: internal var internalVar: ([[BOOL]], [[BOOL]]) = (false, true)
+ // COMMON: internal var internalVar: ([[BOOL]], [[BOOL]]) = (false, true)
internal var internalVar: (Bool, Bool) = (false, true)
- // CHECK: private var privateVar: [[BOOL]] = Bool(4 < 10)
+ // COMMON: private var privateVar: [[BOOL]] = Bool(4 < 10)
private var privateVar: Bool = Bool(4 < 10)
- // CHECK: @usableFromInline
- // CHECK-NEXT: internal var ufiVar: [[BOOL]] = true
+ // COMMON: @usableFromInline
+ // COMMON-NEXT: internal var ufiVar: [[BOOL]] = true
@usableFromInline internal var ufiVar: Bool = true
- // CHECK: public var multiVar1: [[BOOL]] = Bool(false), (multiVar2, multiVar3): ([[BOOL]], [[BOOL]]) = (true, 3 == 0)
+ // COMMON: public var multiVar1: [[BOOL]] = Bool(false), (multiVar2, multiVar3): ([[BOOL]], [[BOOL]]) = (true, 3 == 0)
public var multiVar1: Bool = Bool(false), (multiVar2, multiVar3): (Bool, Bool) = (true, 3 == 0)
- // CHECK: @_hasInitialValue public static var staticVar: [[BOOL]]
+ // NONRESILIENT: @_hasInitialValue public static var staticVar: [[BOOL]]
+ // RESILIENT: {{^}} public static var staticVar: [[BOOL]]
public static var staticVar: Bool = Bool(true && false)
// FROMSOURCE: @inlinable internal init() {}
@@ -39,23 +40,24 @@
@inlinable init() {}
}
-// CHECK: @_fixed_layout public class MyClass {
+// COMMON: @_fixed_layout public class MyClass {
@_fixed_layout
public class MyClass {
- // CHECK: public var publicVar: [[BOOL]] = false
+ // COMMON: public var publicVar: [[BOOL]] = false
public var publicVar: Bool = false
- // CHECK: internal var internalVar: [[BOOL]] = false
+ // COMMON: internal var internalVar: [[BOOL]] = false
internal var internalVar: Bool = false
- // CHECK: private var privateVar: {{(Swift\.)?}}UInt8 = UInt8(2)
+ // COMMON: private var privateVar: {{(Swift\.)?}}UInt8 = UInt8(2)
private var privateVar: UInt8 = UInt8(2)
- // CHECK: @usableFromInline
- // CHECK-NEXT: internal var ufiVar: [[BOOL]] = true
+ // COMMON: @usableFromInline
+ // COMMON-NEXT: internal var ufiVar: [[BOOL]] = true
@usableFromInline internal var ufiVar: Bool = true
- // CHECK: @_hasInitialValue public static var staticVar: [[BOOL]]
+ // NONRESILIENT: @_hasInitialValue public static var staticVar: [[BOOL]]
+ // RESILIENT: {{^}} public static var staticVar: [[BOOL]]
public static var staticVar: Bool = Bool(true && false)
// FROMSOURCE: @inlinable internal init() {}
@@ -63,5 +65,6 @@
@inlinable init() {}
}
-// CHECK: @_hasInitialValue public var topLevelVar: [[BOOL]]
+// NONRESILIENT: @_hasInitialValue public var topLevelVar: [[BOOL]]
+// RESILIENT: {{^}}public var topLevelVar: [[BOOL]]
public var topLevelVar: Bool = Bool(false && !true)
diff --git a/test/ParseableInterface/stored-properties.swift b/test/ParseableInterface/stored-properties.swift
index 774553e..a4392e1 100644
--- a/test/ParseableInterface/stored-properties.swift
+++ b/test/ParseableInterface/stored-properties.swift
@@ -53,7 +53,7 @@
private var privateVar: Bool
// CHECK: @_hasStorage @_hasInitialValue public var storedWithObserversInitialValue: [[INT]] {
- // RESILIENT: {{^}} @_hasInitialValue public var storedWithObserversInitialValue: [[INT]] {
+ // RESILIENT: {{^}} public var storedWithObserversInitialValue: [[INT]] {
// COMMON-NEXT: get
// COMMON-NEXT: set
// COMMON-NEXT: }
diff --git a/test/Reflection/typeref_lowering.swift b/test/Reflection/typeref_lowering.swift
index 7570f5c..64c8c11 100644
--- a/test/Reflection/typeref_lowering.swift
+++ b/test/Reflection/typeref_lowering.swift
@@ -1044,7 +1044,7 @@
// CHECK-64-NEXT: (field name=Indirect offset=0
// CHECK-64-NEXT: (reference kind=strong refcounting=native))))
// CHECK-64-NEXT: (field name=multiPayloadConcrete offset=24
-// CHECK-64-NEXT: (multi_payload_enum size=8 alignment=8 stride=8 num_extra_inhabitants=2045 bitwise_takable=1
+// CHECK-64-NEXT: (multi_payload_enum size=8 alignment=8 stride=8 num_extra_inhabitants={{(2045|125)}} bitwise_takable=1
// CHECK-64-NEXT: (field name=Left offset=0
// CHECK-64-NEXT: (reference kind=strong refcounting=native))
// CHECK-64-NEXT: (field name=Right offset=0
diff --git a/test/Runtime/demangleToMetadataObjC.swift b/test/Runtime/demangleToMetadataObjC.swift
index fba76ef..8a0db73 100644
--- a/test/Runtime/demangleToMetadataObjC.swift
+++ b/test/Runtime/demangleToMetadataObjC.swift
@@ -108,5 +108,9 @@
expectEqual(F<P3>.self, _typeByName("4main1FCyAA2P3PG")!)
}
+DemangleToMetadataTests.test("Objective-C generics") {
+ expectEqual(NSArray.self, _typeByName("So7NSArrayCySo8NSStringCG")!)
+}
+
runAllTests()
diff --git a/test/SIL/Parser/overloaded_member.sil b/test/SIL/Parser/overloaded_member.sil
index 1e0dffe..05e8b03 100644
--- a/test/SIL/Parser/overloaded_member.sil
+++ b/test/SIL/Parser/overloaded_member.sil
@@ -37,3 +37,26 @@
destroy_value %2 : $<τ_0_0> { var τ_0_0 } <X>
return %15 : $X
}
+
+// rdar://46650834
+// Don't complain that the first lookup result lacks an accessor when a
+// later lookup result provides it.
+class B {
+ typealias Index = Int
+ typealias Element = String
+
+ subscript(owned index: Index) -> Element { get }
+
+ @_borrowed
+ subscript(borrowed index: Index) -> Element { get }
+}
+
+sil [ossa] @test_overloaded_subscript : $@convention(thin) (@guaranteed B, B.Index) -> () {
+bb0(%0 : $B, %1 : $B.Index):
+ %reader = class_method %0 : $B, #B.subscript!read.1 : (B) -> (B.Index) -> (), $@convention(method) @yield_once (B.Index, @guaranteed B) -> @yields @guaranteed B.Element
+ (%element, %token) = begin_apply %reader(%1, %0) : $@convention(method) @yield_once (B.Index, @guaranteed B) -> @yields @guaranteed B.Element
+ end_apply %token
+
+ %result = tuple ()
+ return %result : $()
+}
diff --git a/test/stdlib/ErrorBridged.swift b/test/stdlib/ErrorBridged.swift
index 6a90d1c..958ed7c 100644
--- a/test/stdlib/ErrorBridged.swift
+++ b/test/stdlib/ErrorBridged.swift
@@ -722,4 +722,49 @@
=== nsError)
}
+// SR-9389
+class ParentA: NSObject {
+ @objc(ParentAError) enum Error: Int, Swift.Error {
+ case failed
+ }
+}
+class ParentB: NSObject {
+ @objc(ParentBError) enum Error: Int, Swift.Error {
+ case failed
+ }
+}
+private class NonPrintAsObjCClass: NSObject {
+ @objc enum Error: Int, Swift.Error {
+ case foo
+ }
+}
+@objc private enum NonPrintAsObjCError: Int, Error {
+ case bar
+}
+
+ErrorBridgingTests.test("@objc error domains for nested types") {
+ // Domain strings should correspond to Swift types, including parent types.
+ expectEqual(ParentA.Error.failed._domain, "main.ParentA.Error")
+ expectEqual(ParentB.Error.failed._domain, "main.ParentB.Error")
+
+ func makeNSError(like error: Error) -> NSError {
+ return NSError(domain: error._domain, code: error._code)
+ }
+
+ // NSErrors corresponding to Error types with the same name but nested in
+ // different enclosing types should not be castable to the wrong error type.
+ expectTrue(makeNSError(like: ParentA.Error.failed) is ParentA.Error)
+ expectFalse(makeNSError(like: ParentA.Error.failed) is ParentB.Error)
+ expectFalse(makeNSError(like: ParentB.Error.failed) is ParentA.Error)
+ expectTrue(makeNSError(like: ParentB.Error.failed) is ParentB.Error)
+
+ // If an @objc enum error is not eligible for PrintAsObjC, we should treat it
+ // as though it inherited the default implementation, which calls
+ // String(reflecting:).
+ expectEqual(NonPrintAsObjCClass.Error.foo._domain,
+ String(reflecting: NonPrintAsObjCClass.Error.self))
+ expectEqual(NonPrintAsObjCError.bar._domain,
+ String(reflecting: NonPrintAsObjCError.self))
+}
+
runAllTests()
diff --git a/test/stdlib/UnavailableStringAPIs.swift.gyb b/test/stdlib/UnavailableStringAPIs.swift.gyb
index 537fbb4..c1adb14 100644
--- a/test/stdlib/UnavailableStringAPIs.swift.gyb
+++ b/test/stdlib/UnavailableStringAPIs.swift.gyb
@@ -2,8 +2,6 @@
// RUN: %gyb -D_runtime=%target-runtime %s -o %t/main.swift
// RUN: %line-directive %t/main.swift -- %target-swift-frontend -typecheck -verify %t/main.swift
-// REQUIRES: rdar44572521
-
func test_StringSubscriptByInt(
x: String,
i: Int,
@@ -15,13 +13,6 @@
_ = x[r2] // expected-error {{'subscript(_:)' is unavailable: cannot subscript String with an integer range, see the documentation comment for discussion}} {{none}}
}
-% if _runtime == 'objc':
-func test_UTF16ViewSubscriptByInt(x: String.UTF16View, i: Int, r: Range<Int>) {
- _ = x[i] // expected-error {{'subscript(_:)' is unavailable: Indexing a String's UTF16View requires a String.UTF16View.Index, which can be constructed from Int when Foundation is imported}} {{none}}
- _ = x[r] // expected-error {{'subscript(_:)' is unavailable: Slicing a String's UTF16View requires a Range<String.UTF16View.Index>, String.UTF16View.Index can be constructed from Int when Foundation is imported}} {{none}}
-}
-% end
-
func test_UTF8View(s: String.UTF8View, i: String.UTF8View.Index, d: Int) {
_ = s.index(after: i) // OK
_ = s.index(before: i) // OK
diff --git a/utils/build-toolchain b/utils/build-toolchain
index 68284db..4edcc95 100755
--- a/utils/build-toolchain
+++ b/utils/build-toolchain
@@ -41,9 +41,11 @@
case $(uname -s) in
Darwin)
SWIFT_PACKAGE=buildbot_osx_package,no_test
+ OS_SUFFIX=osx
;;
Linux)
SWIFT_PACKAGE=buildbot_linux,no_test
+ OS_SUFFIX=linux
;;
*)
echo "Unrecognised platform $(uname -s)"
@@ -98,8 +100,8 @@
DAY=$(date +"%d")
TOOLCHAIN_VERSION="swift-LOCAL-${YEAR}-${MONTH}-${DAY}-a"
DARWIN_TOOLCHAIN_VERSION="0.0.${YEAR}${MONTH}${DAY}"
-ARCHIVE="${TOOLCHAIN_VERSION}-osx.tar.gz"
-SYM_ARCHIVE="${TOOLCHAIN_VERSION}-osx-symbols.tar.gz"
+ARCHIVE="${TOOLCHAIN_VERSION}-${OS_SUFFIX}.tar.gz"
+SYM_ARCHIVE="${TOOLCHAIN_VERSION}-${OS_SUFFIX}-symbols.tar.gz"
BUNDLE_PREFIX=${BUNDLE_PREFIX:?Please specify a bundle prefix}
BUNDLE_IDENTIFIER="${BUNDLE_PREFIX}.${YEAR}${MONTH}${DAY}"
DISPLAY_NAME_SHORT="Local Swift Development Snapshot"