diff --git a/cmake/modules/DarwinSDKs.cmake b/cmake/modules/DarwinSDKs.cmake index 5ad1e32d1d8a1..20a5620fba6a7 100644 --- a/cmake/modules/DarwinSDKs.cmake +++ b/cmake/modules/DarwinSDKs.cmake @@ -16,23 +16,6 @@ set(SUPPORTED_WATCHOS_ARCHS "armv7k") set(SUPPORTED_WATCHOS_SIMULATOR_ARCHS "i386;arm64") set(SUPPORTED_OSX_ARCHS "x86_64;arm64;arm64e") -# Get the SDK version from SDKSettings. -execute_process( - COMMAND "defaults" "read" "${CMAKE_OSX_SYSROOT}/SDKSettings.plist" "Version" - OUTPUT_VARIABLE SWIFT_OSX_SDK_VERSION - OUTPUT_STRIP_TRAILING_WHITESPACE) - -# Remove the last component, if any. e.g. 10.15.26 -> 10.15 -string(REGEX REPLACE "\([0-9]*[.][0-9]*\)[.][0-9]*" "\\1" - SWIFT_OSX_SDK_VERSION "${SWIFT_OSX_SDK_VERSION}") - -if (${SWIFT_OSX_SDK_VERSION} STREQUAL "10.14" OR - ${SWIFT_OSX_SDK_VERSION} STREQUAL "10.15") - set(SUPPORTED_OSX_ARCHS "x86_64") -else() - set(SUPPORTED_OSX_ARCHS "x86_64;arm64e") -endif() - is_sdk_requested(OSX swift_build_osx) if(swift_build_osx) configure_sdk_darwin( diff --git a/include/swift/AST/DiagnosticEngine.h b/include/swift/AST/DiagnosticEngine.h index 6513a5df51ae3..50bbe2037a1e6 100644 --- a/include/swift/AST/DiagnosticEngine.h +++ b/include/swift/AST/DiagnosticEngine.h @@ -1025,10 +1025,19 @@ namespace swift { } } - bool hasDiagnostics() const { - return std::distance(Engine.TentativeDiagnostics.begin() + - PrevDiagnostics, - Engine.TentativeDiagnostics.end()) > 0; + bool hasErrors() const { + ArrayRef diagnostics(Engine.TentativeDiagnostics.begin() + + PrevDiagnostics, + Engine.TentativeDiagnostics.end()); + + for (auto &diagnostic : diagnostics) { + auto behavior = Engine.state.determineBehavior(diagnostic.getID()); + if (behavior == DiagnosticState::Behavior::Fatal || + behavior == DiagnosticState::Behavior::Error) + return true; + } + + return false; } /// Abort and close this transaction and erase all diagnostics diff --git a/include/swift/AST/DiagnosticsFrontend.def b/include/swift/AST/DiagnosticsFrontend.def index 4ed1d7a62d92e..d5771f82d955e 100644 --- a/include/swift/AST/DiagnosticsFrontend.def +++ b/include/swift/AST/DiagnosticsFrontend.def @@ -301,6 +301,9 @@ ERROR(error_optimization_remark_pattern, none, "%0 in '%1'", ERROR(error_invalid_debug_prefix_map, none, "invalid argument '%0' to -debug-prefix-map; it must be of the form " "'original=remapped'", (StringRef)) +ERROR(error_invalid_coverage_prefix_map, none, + "invalid argument '%0' to -coverage-prefix-map; it must be of the form " + "'original=remapped'", (StringRef)) ERROR(error_unable_to_write_swift_ranges_file, none, diff --git a/include/swift/AST/IRGenOptions.h b/include/swift/AST/IRGenOptions.h index dc5e2fa745403..df3a145cab6b2 100644 --- a/include/swift/AST/IRGenOptions.h +++ b/include/swift/AST/IRGenOptions.h @@ -169,6 +169,9 @@ class IRGenOptions { /// Path prefixes that should be rewritten in debug info. PathRemapper DebugPrefixMap; + /// Path prefixes that should be rewritten in coverage info. + PathRemapper CoveragePrefixMap; + /// What level of debug info to generate. IRGenDebugInfoLevel DebugInfoLevel : 2; diff --git a/include/swift/Frontend/Frontend.h b/include/swift/Frontend/Frontend.h index 7718407233f5d..b2046d0ff8e68 100644 --- a/include/swift/Frontend/Frontend.h +++ b/include/swift/Frontend/Frontend.h @@ -128,7 +128,8 @@ class CompilerInvocation { bool parseArgs(ArrayRef Args, DiagnosticEngine &Diags, SmallVectorImpl> *ConfigurationFileBuffers = nullptr, - StringRef workingDirectory = {}); + StringRef workingDirectory = {}, + StringRef mainExecutablePath = {}); /// Sets specific options based on the given serialized Swift binary data. /// @@ -213,8 +214,11 @@ class CompilerInvocation { /// Computes the runtime resource path relative to the given Swift /// executable. static void computeRuntimeResourcePathFromExecutablePath( - StringRef mainExecutablePath, - llvm::SmallString<128> &runtimeResourcePath); + StringRef mainExecutablePath, bool shared, + llvm::SmallVectorImpl &runtimeResourcePath); + + /// Appends `lib/swift[_static]` to the given path + static void appendSwiftLibDir(llvm::SmallVectorImpl &path, bool shared); void setSDKPath(const std::string &Path); diff --git a/include/swift/Frontend/FrontendOptions.h b/include/swift/Frontend/FrontendOptions.h index 81f72772239a0..51ff57eb20a58 100644 --- a/include/swift/Frontend/FrontendOptions.h +++ b/include/swift/Frontend/FrontendOptions.h @@ -301,6 +301,11 @@ class FrontendOptions { /// Indicates whether the action will immediately run code. static bool isActionImmediate(ActionType); + /// Determines whether the static or shared resource folder is used. + /// When set to `true`, the default resource folder will be set to + /// '.../lib/swift', otherwise '.../lib/swift_static'. + bool UseSharedResourceFolder = true; + /// \return true if action only parses without doing other compilation steps. static bool shouldActionOnlyParse(ActionType); diff --git a/include/swift/Option/FrontendOptions.td b/include/swift/Option/FrontendOptions.td index 8190787c330fc..3ac11f1ecba6c 100644 --- a/include/swift/Option/FrontendOptions.td +++ b/include/swift/Option/FrontendOptions.td @@ -719,4 +719,8 @@ def target_sdk_version : Separate<["-"], "target-sdk-version">, def target_variant_sdk_version : Separate<["-"], "target-variant-sdk-version">, HelpText<"The version of target variant SDK used for compilation">; + +def use_static_resource_dir + : Flag<["-"], "use-static-resource-dir">, + HelpText<"Use resources in the static resource directory">; } // end let Flags = [FrontendOption, NoDriverOption, HelpHidden] diff --git a/include/swift/Option/Options.td b/include/swift/Option/Options.td index fcfbaa438f350..11c6d10701cd2 100644 --- a/include/swift/Option/Options.td +++ b/include/swift/Option/Options.td @@ -708,6 +708,9 @@ def gdwarf_types : Flag<["-"], "gdwarf-types">, def debug_prefix_map : Separate<["-"], "debug-prefix-map">, Flags<[FrontendOption]>, HelpText<"Remap source paths in debug info">; +def coverage_prefix_map : Separate<["-"], "coverage-prefix-map">, + Flags<[FrontendOption]>, + HelpText<"Remap source paths in coverage info">; def debug_info_format : Joined<["-"], "debug-info-format=">, Flags<[FrontendOption]>, diff --git a/lib/AST/Type.cpp b/lib/AST/Type.cpp index 30b3ee134ebf2..773aca7a2e8a7 100644 --- a/lib/AST/Type.cpp +++ b/lib/AST/Type.cpp @@ -3059,8 +3059,8 @@ operator()(SubstitutableType *maybeOpaqueType) const { })) return maybeOpaqueType; - // If the type still contains opaque types, recur. - if (substTy->hasOpaqueArchetype()) { + // If the type changed, but still contains opaque types, recur. + if (!substTy->isEqual(maybeOpaqueType) && substTy->hasOpaqueArchetype()) { return ::substOpaqueTypesWithUnderlyingTypes( substTy, inContext, contextExpansion, isContextWholeModule); } diff --git a/lib/Driver/Driver.cpp b/lib/Driver/Driver.cpp index 65c598f4fac63..59faa6ed79bfc 100644 --- a/lib/Driver/Driver.cpp +++ b/lib/Driver/Driver.cpp @@ -179,6 +179,12 @@ static void validateDebugInfoArgs(DiagnosticEngine &diags, for (auto A : args.getAllArgValues(options::OPT_debug_prefix_map)) if (A.find('=') == StringRef::npos) diags.diagnose(SourceLoc(), diag::error_invalid_debug_prefix_map, A); + + // Check for any -coverage-prefix-map options that aren't of the form + // 'original=remapped' (either side can be empty, however). + for (auto A : args.getAllArgValues(options::OPT_coverage_prefix_map)) + if (A.find('=') == StringRef::npos) + diags.diagnose(SourceLoc(), diag::error_invalid_coverage_prefix_map, A); } static void validateVerifyIncrementalDependencyArgs(DiagnosticEngine &diags, @@ -2233,6 +2239,13 @@ bool Driver::handleImmediateArgs(const ArgList &Args, const ToolChain &TC) { commandLine.push_back(resourceDirArg->getValue()); } + if (Args.hasFlag(options::OPT_static_executable, + options::OPT_no_static_executable, false) || + Args.hasFlag(options::OPT_static_stdlib, options::OPT_no_static_stdlib, + false)) { + commandLine.push_back("-use-static-resource-dir"); + } + std::string executable = getSwiftProgramPath(); // FIXME: This bypasses mechanisms like -v and -###. (SR-12119) diff --git a/lib/Driver/ToolChains.cpp b/lib/Driver/ToolChains.cpp index 9c9e95fc58394..c60397c2a3108 100644 --- a/lib/Driver/ToolChains.cpp +++ b/lib/Driver/ToolChains.cpp @@ -22,6 +22,7 @@ #include "swift/Driver/Compilation.h" #include "swift/Driver/Driver.h" #include "swift/Driver/Job.h" +#include "swift/Frontend/Frontend.h" #include "swift/Option/Options.h" #include "clang/Basic/Version.h" #include "clang/Driver/Util.h" @@ -264,6 +265,7 @@ void ToolChain::addCommonFrontendArgs(const OutputInfo &OI, // Pass on file paths that should be remapped in debug info. inputArgs.AddAllArgs(arguments, options::OPT_debug_prefix_map); + inputArgs.AddAllArgs(arguments, options::OPT_coverage_prefix_map); // Pass through the values passed to -Xfrontend. inputArgs.AddAllArgValues(arguments, options::OPT_Xfrontend); @@ -523,6 +525,13 @@ ToolChain::constructInvocation(const CompileJobAction &job, Arguments.push_back("-track-system-dependencies"); } + if (context.Args.hasFlag(options::OPT_static_executable, + options::OPT_no_static_executable, false) || + context.Args.hasFlag(options::OPT_static_stdlib, + options::OPT_no_static_stdlib, false)) { + Arguments.push_back("-use-static-resource-dir"); + } + context.Args.AddLastArg( Arguments, options:: @@ -1256,9 +1265,6 @@ void ToolChain::getClangLibraryPath(const ArgList &Args, void ToolChain::getResourceDirPath(SmallVectorImpl &resourceDirPath, const llvm::opt::ArgList &args, bool shared) const { - // FIXME: Duplicated from CompilerInvocation, but in theory the runtime - // library link path and the standard library module import path don't - // need to be the same. if (const Arg *A = args.getLastArg(options::OPT_resource_dir)) { StringRef value = A->getValue(); resourceDirPath.append(value.begin(), value.end()); @@ -1266,15 +1272,12 @@ void ToolChain::getResourceDirPath(SmallVectorImpl &resourceDirPath, // for WASI, sdk option points to wasi-sysroot which doesn't have Swift toolchain StringRef value = args.getLastArg(options::OPT_sdk)->getValue(); resourceDirPath.append(value.begin(), value.end()); - llvm::sys::path::append(resourceDirPath, "usr", "lib", - shared ? "swift" : "swift_static"); + llvm::sys::path::append(resourceDirPath, "usr"); + CompilerInvocation::appendSwiftLibDir(resourceDirPath, shared); } else { auto programPath = getDriver().getSwiftProgramPath(); - resourceDirPath.append(programPath.begin(), programPath.end()); - llvm::sys::path::remove_filename(resourceDirPath); // remove /swift - llvm::sys::path::remove_filename(resourceDirPath); // remove /bin - llvm::sys::path::append(resourceDirPath, "lib", - shared ? "swift" : "swift_static"); + CompilerInvocation::computeRuntimeResourcePathFromExecutablePath( + programPath, shared, resourceDirPath); } StringRef libSubDir = getPlatformNameForTriple(getTriple()); diff --git a/lib/Frontend/ArgsToFrontendOptionsConverter.cpp b/lib/Frontend/ArgsToFrontendOptionsConverter.cpp index 7113e2d4c0c07..eabc8a5514bcc 100644 --- a/lib/Frontend/ArgsToFrontendOptionsConverter.cpp +++ b/lib/Frontend/ArgsToFrontendOptionsConverter.cpp @@ -187,6 +187,7 @@ bool ArgsToFrontendOptionsConverter::convert( Opts.EnableSourceImport |= Args.hasArg(OPT_enable_source_import); Opts.ImportUnderlyingModule |= Args.hasArg(OPT_import_underlying_module); Opts.EnableIncrementalDependencyVerifier |= Args.hasArg(OPT_verify_incremental_dependencies); + Opts.UseSharedResourceFolder = !Args.hasArg(OPT_use_static_resource_dir); computeImportObjCHeaderOptions(); computeImplicitImportModuleNames(); diff --git a/lib/Frontend/CompilerInvocation.cpp b/lib/Frontend/CompilerInvocation.cpp index 391fc4d3a5cfd..e39d6bb8d868e 100644 --- a/lib/Frontend/CompilerInvocation.cpp +++ b/lib/Frontend/CompilerInvocation.cpp @@ -39,16 +39,25 @@ swift::CompilerInvocation::CompilerInvocation() { } void CompilerInvocation::computeRuntimeResourcePathFromExecutablePath( - StringRef mainExecutablePath, llvm::SmallString<128> &runtimeResourcePath) { - runtimeResourcePath.assign(mainExecutablePath); + StringRef mainExecutablePath, bool shared, + llvm::SmallVectorImpl &runtimeResourcePath) { + runtimeResourcePath.append(mainExecutablePath.begin(), + mainExecutablePath.end()); + llvm::sys::path::remove_filename(runtimeResourcePath); // Remove /swift llvm::sys::path::remove_filename(runtimeResourcePath); // Remove /bin - llvm::sys::path::append(runtimeResourcePath, "lib", "swift"); + appendSwiftLibDir(runtimeResourcePath, shared); +} + +void CompilerInvocation::appendSwiftLibDir(llvm::SmallVectorImpl &path, + bool shared) { + llvm::sys::path::append(path, "lib", shared ? "swift" : "swift_static"); } void CompilerInvocation::setMainExecutablePath(StringRef Path) { llvm::SmallString<128> LibPath; - computeRuntimeResourcePathFromExecutablePath(Path, LibPath); + computeRuntimeResourcePathFromExecutablePath( + Path, FrontendOpts.UseSharedResourceFolder, LibPath); setRuntimeResourcePath(LibPath.str()); llvm::SmallString<128> DiagnosticDocsPath(Path); @@ -1258,6 +1267,11 @@ static bool ParseIRGenArgs(IRGenOptions &Opts, ArgList &Args, Opts.DebugPrefixMap.addMapping(SplitMap.first, SplitMap.second); } + for (auto A : Args.getAllArgValues(options::OPT_coverage_prefix_map)) { + auto SplitMap = StringRef(A).split('='); + Opts.CoveragePrefixMap.addMapping(SplitMap.first, SplitMap.second); + } + for (const Arg *A : Args.filtered(OPT_Xcc)) { StringRef Opt = A->getValue(); if (Opt.startswith("-D") || Opt.startswith("-U")) @@ -1584,11 +1598,10 @@ static bool ParseMigratorArgs(MigratorOptions &Opts, } bool CompilerInvocation::parseArgs( - ArrayRef Args, - DiagnosticEngine &Diags, + ArrayRef Args, DiagnosticEngine &Diags, SmallVectorImpl> *ConfigurationFileBuffers, - StringRef workingDirectory) { + StringRef workingDirectory, StringRef mainExecutablePath) { using namespace options; if (Args.empty()) @@ -1619,6 +1632,10 @@ bool CompilerInvocation::parseArgs( return true; } + if (!mainExecutablePath.empty()) { + setMainExecutablePath(mainExecutablePath); + } + ParseModuleInterfaceArgs(ModuleInterfaceOpts, ParsedArgs); SaveModuleInterfaceArgs(ModuleInterfaceOpts, FrontendOpts, ParsedArgs, Diags); diff --git a/lib/FrontendTool/FrontendTool.cpp b/lib/FrontendTool/FrontendTool.cpp index e78174844befa..7d8d63656f4ee 100644 --- a/lib/FrontendTool/FrontendTool.cpp +++ b/lib/FrontendTool/FrontendTool.cpp @@ -2078,17 +2078,18 @@ int swift::performFrontend(ArrayRef Args, } CompilerInvocation Invocation; - std::string MainExecutablePath = llvm::sys::fs::getMainExecutable(Argv0, - MainAddr); - Invocation.setMainExecutablePath(MainExecutablePath); SmallString<128> workingDirectory; llvm::sys::fs::current_path(workingDirectory); + std::string MainExecutablePath = + llvm::sys::fs::getMainExecutable(Argv0, MainAddr); + // Parse arguments. SmallVector, 4> configurationFileBuffers; if (Invocation.parseArgs(Args, Instance->getDiags(), - &configurationFileBuffers, workingDirectory)) { + &configurationFileBuffers, workingDirectory, + MainExecutablePath)) { return finishDiagProcessing(1, /*verifierEnabled*/ false); } diff --git a/lib/IRGen/GenClangDecl.cpp b/lib/IRGen/GenClangDecl.cpp index 00b5a0e697352..4a34195b39fe9 100644 --- a/lib/IRGen/GenClangDecl.cpp +++ b/lib/IRGen/GenClangDecl.cpp @@ -34,18 +34,43 @@ class ClangDeclRefFinder return true; } }; + +// If any (re)declaration of `decl` contains executable code, returns that +// redeclaration; otherwise, returns nullptr. +// In the case of a function, executable code is contained in the function +// definition. In the case of a variable, executable code can be contained in +// the initializer of the variable. +clang::Decl *getDeclWithExecutableCode(clang::Decl *decl) { + if (auto fd = dyn_cast(decl)) { + const clang::FunctionDecl *definition; + if (fd->hasBody(definition)) { + return const_cast(definition); + } + } else if (auto vd = dyn_cast(decl)) { + clang::VarDecl *initializingDecl = vd->getInitializingDeclaration(); + if (initializingDecl) { + return initializingDecl; + } + } + + return nullptr; +} + } // end anonymous namespace void IRGenModule::emitClangDecl(const clang::Decl *decl) { - auto valueDecl = dyn_cast(decl); - if (!valueDecl || valueDecl->isExternallyVisible()) { + // Ignore this decl if we've seen it before. + if (!GlobalClangDecls.insert(decl->getCanonicalDecl()).second) + return; + + // Fast path for the case where `decl` doesn't contain executable code, so it + // can't reference any other declarations that we would need to emit. + if (getDeclWithExecutableCode(const_cast(decl)) == nullptr) { ClangCodeGen->HandleTopLevelDecl( clang::DeclGroupRef(const_cast(decl))); return; } - if (!GlobalClangDecls.insert(decl->getCanonicalDecl()).second) - return; SmallVector stack; stack.push_back(decl); @@ -69,13 +94,15 @@ void IRGenModule::emitClangDecl(const clang::Decl *decl) { while (!stack.empty()) { auto *next = const_cast(stack.pop_back_val()); - if (auto fn = dyn_cast(next)) { - const clang::FunctionDecl *definition; - if (fn->hasBody(definition)) { - refFinder.TraverseDecl(const_cast(definition)); - next = const_cast(definition); - } + if (clang::Decl *executableDecl = getDeclWithExecutableCode(next)) { + refFinder.TraverseDecl(executableDecl); + next = executableDecl; } + + if (auto var = dyn_cast(next)) + if (!var->isFileVarDecl()) + continue; + ClangCodeGen->HandleTopLevelDecl(clang::DeclGroupRef(next)); } } diff --git a/lib/IRGen/GenCoverage.cpp b/lib/IRGen/GenCoverage.cpp index 699d1584e4eb1..a5d2e6d512f6e 100644 --- a/lib/IRGen/GenCoverage.cpp +++ b/lib/IRGen/GenCoverage.cpp @@ -18,6 +18,7 @@ #include "IRGenModule.h" #include "SwiftTargetInfo.h" +#include "swift/AST/IRGenOptions.h" #include "swift/SIL/SILModule.h" #include "llvm/IR/Constants.h" #include "llvm/IR/Module.h" @@ -60,6 +61,7 @@ void IRGenModule::emitCoverageMapping() { if (std::find(Files.begin(), Files.end(), M->getFile()) == Files.end()) Files.push_back(M->getFile()); + auto remapper = getOptions().CoveragePrefixMap; // Awkwardly munge absolute filenames into a vector of StringRefs. // TODO: This is heinous - the same thing is happening in clang, but the API // really needs to be cleaned up for both. @@ -68,7 +70,7 @@ void IRGenModule::emitCoverageMapping() { for (StringRef Name : Files) { llvm::SmallString<256> Path(Name); llvm::sys::fs::make_absolute(Path); - FilenameStrs.push_back(std::string(Path.begin(), Path.end())); + FilenameStrs.push_back(remapper.remapPath(Path)); FilenameRefs.push_back(FilenameStrs.back()); } diff --git a/lib/IRGen/GenDecl.cpp b/lib/IRGen/GenDecl.cpp index 952383bc98429..b004693063472 100644 --- a/lib/IRGen/GenDecl.cpp +++ b/lib/IRGen/GenDecl.cpp @@ -1104,8 +1104,11 @@ void IRGenerator::emitGlobalTopLevel(llvm::StringSet<> *linkerDirectives) { IGM->emitSILDifferentiabilityWitness(&dw); } - // Emit code coverage mapping data. - PrimaryIGM->emitCoverageMapping(); + // Emit code coverage mapping data for all modules + for (auto Iter : *this) { + IRGenModule *IGM = Iter.second; + IGM->emitCoverageMapping(); + } for (auto Iter : *this) { IRGenModule *IGM = Iter.second; diff --git a/lib/SILOptimizer/SILCombiner/SILCombinerApplyVisitors.cpp b/lib/SILOptimizer/SILCombiner/SILCombinerApplyVisitors.cpp index 7539481abbe45..83227a30d6a9a 100644 --- a/lib/SILOptimizer/SILCombiner/SILCombinerApplyVisitors.cpp +++ b/lib/SILOptimizer/SILCombiner/SILCombinerApplyVisitors.cpp @@ -584,6 +584,8 @@ void SILCombiner::buildConcreteOpenedExistentialInfos( // BuilderContext before rewriting any uses of the ConcreteType. OpenedArchetypesTracker.addOpenedArchetypeDef( cast(CEI.ConcreteType), CEI.ConcreteTypeDef); + } else if (auto *I = CEI.ConcreteValue->getDefiningInstruction()) { + OpenedArchetypesTracker.registerUsedOpenedArchetypes(I); } } } diff --git a/lib/SILOptimizer/SILCombiner/SILCombinerMiscVisitors.cpp b/lib/SILOptimizer/SILCombiner/SILCombinerMiscVisitors.cpp index 743e4a83d0b5a..4b74af088ee2e 100644 --- a/lib/SILOptimizer/SILCombiner/SILCombinerMiscVisitors.cpp +++ b/lib/SILOptimizer/SILCombiner/SILCombinerMiscVisitors.cpp @@ -480,7 +480,8 @@ SILInstruction *SILCombiner::visitAllocStackInst(AllocStackInst *AS) { // Be careful with open archetypes, because they cannot be moved before // their definitions. if (IEI && !OEI && - !IEI->getLoweredConcreteType().isOpenedExistential()) { + !IEI->getLoweredConcreteType().hasOpenedExistential()) { + assert(!IEI->getLoweredConcreteType().isOpenedExistential()); auto *ConcAlloc = Builder.createAllocStack( AS->getLoc(), IEI->getLoweredConcreteType(), AS->getVarInfo()); IEI->replaceAllUsesWith(ConcAlloc); diff --git a/lib/Sema/BuilderTransform.cpp b/lib/Sema/BuilderTransform.cpp index df7f4f87d76ce..ae1892d0e1312 100644 --- a/lib/Sema/BuilderTransform.cpp +++ b/lib/Sema/BuilderTransform.cpp @@ -1523,6 +1523,14 @@ ConstraintSystem::matchFunctionBuilder( assert(builder && "Bad function builder type"); assert(builder->getAttrs().hasAttribute()); + if (InvalidFunctionBuilderBodies.count(fn)) { + auto *closure = cast(fn.getAbstractClosureExpr()); + (void)recordFix( + IgnoreInvalidFunctionBuilderBody::duringConstraintGeneration( + *this, getConstraintLocator(closure))); + return getTypeMatchSuccess(); + } + // Pre-check the body: pre-check any expressions in it and look // for return statements. auto request = PreCheckFunctionBuilderRequest{fn, fn.getBody(), @@ -1539,7 +1547,7 @@ ConstraintSystem::matchFunctionBuilder( if (auto *closure = dyn_cast_or_null(fn.getAbstractClosureExpr())) { - auto failed = recordFix(IgnoreInvalidFunctionBuilderBody::create( + auto failed = recordFix(IgnoreInvalidFunctionBuilderBody::duringPreCheck( *this, getConstraintLocator(closure))); return failed ? getTypeMatchFailure(locator) : getTypeMatchSuccess(); } @@ -1598,9 +1606,27 @@ ConstraintSystem::matchFunctionBuilder( BuilderClosureVisitor visitor(getASTContext(), this, dc, builderType, bodyResultType); - auto applied = visitor.apply(fn.getBody()); - if (!applied) - return getTypeMatchFailure(locator); + Optional applied = None; + { + DiagnosticTransaction transaction(dc->getASTContext().Diags); + + applied = visitor.apply(fn.getBody()); + if (!applied) + return getTypeMatchFailure(locator); + + if (transaction.hasErrors()) { + if (auto *closure = + dyn_cast_or_null(fn.getAbstractClosureExpr())) { + InvalidFunctionBuilderBodies.insert(fn); + auto failed = recordFix( + IgnoreInvalidFunctionBuilderBody::duringConstraintGeneration( + *this, getConstraintLocator(closure))); + return failed ? getTypeMatchFailure(locator) : getTypeMatchSuccess(); + } + + return getTypeMatchFailure(locator); + } + } Type transformedType = getType(applied->returnExpr); assert(transformedType && "Missing type"); @@ -1687,7 +1713,7 @@ class PreCheckFunctionBuilderApplication : public ASTWalker { HasError |= ConstraintSystem::preCheckExpression( E, DC, /*replaceInvalidRefsWithErrors=*/false); - HasError |= transaction.hasDiagnostics(); + HasError |= transaction.hasErrors(); if (SuppressDiagnostics) transaction.abort(); diff --git a/lib/Sema/CSFix.cpp b/lib/Sema/CSFix.cpp index e97b37626f967..e2091e73e7c29 100644 --- a/lib/Sema/CSFix.cpp +++ b/lib/Sema/CSFix.cpp @@ -1366,6 +1366,14 @@ bool SpecifyKeyPathRootType::diagnose(const Solution &solution, bool IgnoreInvalidFunctionBuilderBody::diagnose(const Solution &solution, bool asNote) const { + switch (Phase) { + // Handled below + case ErrorInPhase::PreCheck: + break; + case ErrorInPhase::ConstraintGeneration: + return true; // Already diagnosed by `matchFunctionBuilder`. + } + auto *S = cast(getAnchor())->getBody(); class PreCheckWalker : public ASTWalker { @@ -1392,7 +1400,7 @@ bool IgnoreInvalidFunctionBuilderBody::diagnose(const Solution &solution, } bool diagnosed() const { - return Transaction.hasDiagnostics(); + return Transaction.hasErrors(); } }; @@ -1403,8 +1411,8 @@ bool IgnoreInvalidFunctionBuilderBody::diagnose(const Solution &solution, return walker.diagnosed(); } -IgnoreInvalidFunctionBuilderBody * -IgnoreInvalidFunctionBuilderBody::create(ConstraintSystem &cs, - ConstraintLocator *locator) { - return new (cs.getAllocator()) IgnoreInvalidFunctionBuilderBody(cs, locator); +IgnoreInvalidFunctionBuilderBody *IgnoreInvalidFunctionBuilderBody::create( + ConstraintSystem &cs, ErrorInPhase phase, ConstraintLocator *locator) { + return new (cs.getAllocator()) + IgnoreInvalidFunctionBuilderBody(cs, phase, locator); } diff --git a/lib/Sema/CSFix.h b/lib/Sema/CSFix.h index 08a582de6a311..727b05a0e62f2 100644 --- a/lib/Sema/CSFix.h +++ b/lib/Sema/CSFix.h @@ -1844,9 +1844,17 @@ class SpecifyKeyPathRootType final : public ConstraintFix { }; class IgnoreInvalidFunctionBuilderBody final : public ConstraintFix { - IgnoreInvalidFunctionBuilderBody(ConstraintSystem &cs, + enum class ErrorInPhase { + PreCheck, + ConstraintGeneration, + }; + + ErrorInPhase Phase; + + IgnoreInvalidFunctionBuilderBody(ConstraintSystem &cs, ErrorInPhase phase, ConstraintLocator *locator) - : ConstraintFix(cs, FixKind::IgnoreInvalidFunctionBuilderBody, locator) {} + : ConstraintFix(cs, FixKind::IgnoreInvalidFunctionBuilderBody, locator), + Phase(phase) {} public: std::string getName() const override { @@ -1859,8 +1867,19 @@ class IgnoreInvalidFunctionBuilderBody final : public ConstraintFix { return diagnose(*commonFixes.front().first); } - static IgnoreInvalidFunctionBuilderBody *create(ConstraintSystem &cs, - ConstraintLocator *locator); + static IgnoreInvalidFunctionBuilderBody * + duringPreCheck(ConstraintSystem &cs, ConstraintLocator *locator) { + return create(cs, ErrorInPhase::PreCheck, locator); + } + + static IgnoreInvalidFunctionBuilderBody * + duringConstraintGeneration(ConstraintSystem &cs, ConstraintLocator *locator) { + return create(cs, ErrorInPhase::ConstraintGeneration, locator); + } + +private: + static IgnoreInvalidFunctionBuilderBody * + create(ConstraintSystem &cs, ErrorInPhase phase, ConstraintLocator *locator); }; } // end namespace constraints diff --git a/lib/Sema/ConstraintSystem.h b/lib/Sema/ConstraintSystem.h index 0428d6570283d..105234a04fca2 100644 --- a/lib/Sema/ConstraintSystem.h +++ b/lib/Sema/ConstraintSystem.h @@ -1727,6 +1727,13 @@ class ConstraintSystem { /// from declared parameters/result and body. llvm::MapVector ClosureTypes; + /// This is a *global* list of all function builder bodies that have + /// been determined to be incorrect by failing constraint generation. + /// + /// Tracking this information is useful to avoid producing duplicate + /// diagnostics when function builder has multiple overloads. + llvm::SmallDenseSet InvalidFunctionBuilderBodies; + /// Maps node types used within all portions of the constraint /// system, instead of directly using the types on the /// nodes themselves. This allows us to typecheck and diff --git a/stdlib/cmake/modules/AddSwiftStdlib.cmake b/stdlib/cmake/modules/AddSwiftStdlib.cmake index 0a2e3b53f5bed..23926fb47b0fb 100644 --- a/stdlib/cmake/modules/AddSwiftStdlib.cmake +++ b/stdlib/cmake/modules/AddSwiftStdlib.cmake @@ -632,6 +632,9 @@ function(_add_swift_target_library_single target name) "${SWIFTLIB_SINGLE_multiple_parameter_options}" ${ARGN}) + translate_flag(${SWIFTLIB_SINGLE_STATIC} "STATIC" + SWIFTLIB_SINGLE_STATIC_keyword) + # Determine macCatalyst build flavor get_maccatalyst_build_flavor(maccatalyst_build_flavor "${SWIFTLIB_SINGLE_SDK}" "${SWIFTLIB_SINGLE_MACCATALYST_BUILD_FLAVOR}") @@ -761,6 +764,7 @@ function(_add_swift_target_library_single target name) ${SWIFTLIB_SINGLE_IS_STDLIB_CORE_keyword} ${SWIFTLIB_SINGLE_IS_SDK_OVERLAY_keyword} ${embed_bitcode_arg} + ${SWIFTLIB_SINGLE_STATIC_keyword} INSTALL_IN_COMPONENT "${SWIFTLIB_SINGLE_INSTALL_IN_COMPONENT}" MACCATALYST_BUILD_FLAVOR "${SWIFTLIB_SINGLE_MACCATALYST_BUILD_FLAVOR}") add_swift_source_group("${SWIFTLIB_SINGLE_EXTERNAL_SOURCES}") diff --git a/stdlib/cmake/modules/SwiftSource.cmake b/stdlib/cmake/modules/SwiftSource.cmake index 89fca8ef221b1..309d336074f80 100644 --- a/stdlib/cmake/modules/SwiftSource.cmake +++ b/stdlib/cmake/modules/SwiftSource.cmake @@ -29,7 +29,7 @@ function(handle_swift_sources dependency_sibgen_target_out_var_name sourcesvar externalvar name) cmake_parse_arguments(SWIFTSOURCES - "IS_MAIN;IS_STDLIB;IS_STDLIB_CORE;IS_SDK_OVERLAY;EMBED_BITCODE" + "IS_MAIN;IS_STDLIB;IS_STDLIB_CORE;IS_SDK_OVERLAY;EMBED_BITCODE;STATIC" "SDK;ARCHITECTURE;INSTALL_IN_COMPONENT;MACCATALYST_BUILD_FLAVOR" "DEPENDS;COMPILE_FLAGS;MODULE_NAME" ${ARGN}) @@ -41,6 +41,8 @@ function(handle_swift_sources IS_SDK_OVERLAY_arg) translate_flag(${SWIFTSOURCES_EMBED_BITCODE} "EMBED_BITCODE" EMBED_BITCODE_arg) + translate_flag(${SWIFTSOURCES_STATIC} "STATIC" + STATIC_arg) if(SWIFTSOURCES_IS_MAIN) set(SWIFTSOURCES_INSTALL_IN_COMPONENT never_install) @@ -280,13 +282,15 @@ endfunction() # [MODULE_NAME] # The module name. # [INSTALL_IN_COMPONENT] # Install produced files. # [EMBED_BITCODE] # Embed LLVM bitcode into the .o files +# [STATIC] # Also write .swiftmodule etc. to static +# # resource folder # ) function(_compile_swift_files dependency_target_out_var_name dependency_module_target_out_var_name dependency_sib_target_out_var_name dependency_sibopt_target_out_var_name dependency_sibgen_target_out_var_name) cmake_parse_arguments(SWIFTFILE - "IS_MAIN;IS_STDLIB;IS_STDLIB_CORE;IS_SDK_OVERLAY;EMBED_BITCODE" + "IS_MAIN;IS_STDLIB;IS_STDLIB_CORE;IS_SDK_OVERLAY;EMBED_BITCODE;STATIC" "OUTPUT;MODULE_NAME;INSTALL_IN_COMPONENT;MACCATALYST_BUILD_FLAVOR" "SOURCES;FLAGS;DEPENDS;SDK;ARCHITECTURE;OPT_FLAGS;MODULE_DIR" ${ARGN}) @@ -450,8 +454,11 @@ function(_compile_swift_files endforeach() set(module_file) + set(module_file_static) set(module_doc_file) + set(module_doc_file_static) set(interface_file) + set(interface_file_static) if(NOT SWIFTFILE_IS_MAIN) # Determine the directory where the module file should be placed. @@ -466,17 +473,28 @@ function(_compile_swift_files list(APPEND swift_flags "-parse-as-library") set(module_base "${module_dir}/${SWIFTFILE_MODULE_NAME}") + + set(module_dir_static "${SWIFTSTATICLIB_DIR}/${library_subdir}") + set(module_base_static "${module_dir_static}/${SWIFTFILE_MODULE_NAME}") + set(module_triple ${SWIFT_SDK_${library_subdir_sdk}_ARCH_${SWIFTFILE_ARCHITECTURE}_MODULE}) if(SWIFTFILE_SDK IN_LIST SWIFT_APPLE_PLATFORMS OR SWIFTFILE_SDK STREQUAL "MACCATALYST") set(specific_module_dir "${module_base}.swiftmodule") set(module_base "${module_base}.swiftmodule/${module_triple}") + + set(specific_module_dir_static "${module_base_static}.swiftmodule") + set(module_base_static "${module_base_static}.swiftmodule/${module_triple}") else() set(specific_module_dir) + set(specific_module_dir_static) endif() set(module_file "${module_base}.swiftmodule") set(module_doc_file "${module_base}.swiftdoc") + set(module_file_static "${module_base_static}.swiftmodule") + set(module_doc_file_static "${module_base_static}.swiftdoc") + # FIXME: These don't really belong inside the swiftmodule, but there's not # an obvious alternate place to put them. set(sib_file "${module_base}.Onone.sib") @@ -485,6 +503,7 @@ function(_compile_swift_files if(SWIFT_ENABLE_MODULE_INTERFACES) set(interface_file "${module_base}.swiftinterface") + set(interface_file_static "${module_base_static}.swiftinterface") list(APPEND swift_module_flags "-emit-module-interface-path" "${interface_file}") endif() @@ -512,10 +531,20 @@ function(_compile_swift_files swift_install_in_component(DIRECTORY "${specific_module_dir}" DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/${library_subdir}" COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}") + if(SWIFTFILE_STATIC) + swift_install_in_component(DIRECTORY "${specific_module_dir_static}" + DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift_static/${library_subdir}" + COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}") + endif() else() swift_install_in_component(FILES ${module_outputs} DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/${library_subdir}" COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}") + if(SWIFTFILE_STATIC) + swift_install_in_component(FILES ${module_outputs} + DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift_static/${library_subdir}" + COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}") + endif() endif() # macCatalyst zippered module setup @@ -565,8 +594,10 @@ function(_compile_swift_files endif() set(module_outputs "${module_file}" "${module_doc_file}") + set(module_outputs_static "${module_file_static}" "${module_doc_file_static}") if(interface_file) list(APPEND module_outputs "${interface_file}") + list(APPEND module_outputs_static "${interface_file_static}") endif() if(SWIFTFILE_SDK IN_LIST SWIFT_APPLE_PLATFORMS) @@ -575,10 +606,23 @@ function(_compile_swift_files COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}" OPTIONAL PATTERN "Project" EXCLUDE) + + if(SWIFTFILE_STATIC) + swift_install_in_component(DIRECTORY "${specific_module_dir_static}" + DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift_static/${library_subdir}" + COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}" + OPTIONAL + PATTERN "Project" EXCLUDE) + endif() else() swift_install_in_component(FILES ${module_outputs} DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/${library_subdir}" COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}") + if(SWIFTFILE_STATIC) + swift_install_in_component(FILES ${module_outputs} + DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift_static/${library_subdir}" + COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}") + endif() endif() set(line_directive_tool "${SWIFT_SOURCE_DIR}/utils/line-directive") @@ -760,7 +804,27 @@ function(_compile_swift_files ${swift_ide_test_dependency} ${create_dirs_dependency_target} COMMENT "Generating ${module_file}") - set("${dependency_module_target_out_var_name}" "${module_dependency_target}" PARENT_SCOPE) + + if(SWIFTFILE_STATIC) + add_custom_command_target( + module_dependency_target_static + COMMAND + "${CMAKE_COMMAND}" "-E" "make_directory" ${module_dir_static} + ${specific_module_dir_static} + COMMAND + "${CMAKE_COMMAND}" "-E" "copy" ${module_file} ${module_file_static} + COMMAND + "${CMAKE_COMMAND}" "-E" "copy" ${module_doc_file} ${module_doc_file_static} + COMMAND + "${CMAKE_COMMAND}" "-E" "copy" ${interface_file} ${interface_file_static} + OUTPUT ${module_outputs_static} + DEPENDS + "${module_dependency_target}" + COMMENT "Generating ${module_file}") + set("${dependency_module_target_out_var_name}" "${module_dependency_target_static}" PARENT_SCOPE) + else() + set("${dependency_module_target_out_var_name}" "${module_dependency_target}" PARENT_SCOPE) + endif() # macCatalyst zippered swiftmodule if(maccatalyst_build_flavor STREQUAL "zippered") diff --git a/stdlib/public/Platform/CMakeLists.txt b/stdlib/public/Platform/CMakeLists.txt index 92bc62e3f7ffe..d9dfcdf34dbef 100644 --- a/stdlib/public/Platform/CMakeLists.txt +++ b/stdlib/public/Platform/CMakeLists.txt @@ -79,6 +79,7 @@ foreach(sdk ${SWIFT_SDKS}) foreach(arch ${SWIFT_SDK_${sdk}_ARCHITECTURES}) set(arch_subdir "${SWIFT_SDK_${sdk}_LIB_SUBDIR}/${arch}") set(module_dir "${SWIFTLIB_DIR}/${arch_subdir}") + set(module_dir_static "${SWIFTSTATICLIB_DIR}/${arch_subdir}") if(${sdk} STREQUAL ANDROID) set(glibc_modulemap_source "bionic.modulemap.gyb") @@ -88,6 +89,7 @@ foreach(sdk ${SWIFT_SDKS}) set(glibc_modulemap_source "glibc.modulemap.gyb") endif() set(glibc_modulemap_out "${module_dir}/glibc.modulemap") + set(glibc_modulemap_out_static "${module_dir_static}/glibc.modulemap") # Configure the module map based on the target. Each platform needs to # reference different headers, based on what's available in their glibc. @@ -103,6 +105,21 @@ foreach(sdk ${SWIFT_SDKS}) list(APPEND glibc_modulemap_target_list ${glibc_modulemap_target}) + if(SWIFT_BUILD_STATIC_STDLIB) + add_custom_command_target( + copy_glibc_modulemap_static + COMMAND + "${CMAKE_COMMAND}" "-E" "make_directory" ${module_dir_static} + COMMAND + "${CMAKE_COMMAND}" "-E" "copy" ${glibc_modulemap_out} ${glibc_modulemap_out_static} + OUTPUT ${glibc_modulemap_out_static} + DEPENDS + "${glibc_modulemap_target}" + COMMENT "Copying Glibc modulemap to static resources") + + list(APPEND glibc_modulemap_target_list ${copy_glibc_modulemap_static}) + endif() + # If this SDK is a target for a non-native host, except if it's for Android # with its own native sysroot, create a native modulemap without a sysroot # prefix. This is the one we'll install instead. @@ -135,6 +152,11 @@ foreach(sdk ${SWIFT_SDKS}) DESTINATION "lib/swift/${arch_subdir}" COMPONENT sdk-overlay) + if(SWIFT_BUILD_STATIC_STDLIB) + swift_install_in_component(FILES "${glibc_modulemap_out}" + DESTINATION "lib/swift_static/${arch_subdir}" + COMPONENT sdk-overlay) + endif() endforeach() endforeach() add_custom_target(glibc_modulemap DEPENDS ${glibc_modulemap_target_list}) diff --git a/stdlib/public/SwiftShims/CMakeLists.txt b/stdlib/public/SwiftShims/CMakeLists.txt index b6d3edc47818c..23ac72bcda599 100644 --- a/stdlib/public/SwiftShims/CMakeLists.txt +++ b/stdlib/public/SwiftShims/CMakeLists.txt @@ -55,10 +55,18 @@ set(sources module.modulemap ) set(output_dir "${SWIFTLIB_DIR}/shims") +set(output_dir_static "${SWIFTSTATICLIB_DIR}/shims") add_custom_command( OUTPUT "${output_dir}" COMMAND ${CMAKE_COMMAND} "-E" "make_directory" "${output_dir}") + +if(SWIFT_BUILD_STATIC_STDLIB) + add_custom_command( + OUTPUT "${output_dir_static}" + COMMAND ${CMAKE_COMMAND} "-E" "make_directory" "${output_dir_static}") +endif() + set(outputs) foreach(input ${sources}) add_custom_command( @@ -70,6 +78,18 @@ foreach(input ${sources}) "${output_dir}/${input}" COMMENT "Copying ${input} to ${output_dir}") list(APPEND outputs "${output_dir}/${input}") + + if(SWIFT_BUILD_STATIC_STDLIB) + add_custom_command( + OUTPUT "${output_dir_static}/${input}" + DEPENDS "${CMAKE_CURRENT_SOURCE_DIR}/${input}" + COMMAND + "${CMAKE_COMMAND}" "-E" "copy_if_different" + "${CMAKE_CURRENT_SOURCE_DIR}/${input}" + "${output_dir_static}/${input}" + COMMENT "Copying ${input} to ${output_dir_static}") + list(APPEND outputs "${output_dir_static}/${input}") + endif() endforeach() # Put the output dir itself last so that it isn't considered the primary output. list(APPEND outputs "${output_dir}") @@ -121,8 +141,25 @@ add_custom_command_target(unused_var CUSTOM_TARGET_NAME "symlink_clang_headers" OUTPUT "${SWIFTLIB_DIR}/clang" COMMENT "Symlinking Clang resource headers into ${SWIFTLIB_DIR}/clang") + add_dependencies(copy_shim_headers symlink_clang_headers) +if(SWIFT_BUILD_STATIC_STDLIB) + add_custom_command_target(unused_var + COMMAND + "${CMAKE_COMMAND}" "-E" "make_directory" "${SWIFTSTATICLIB_DIR}" + COMMAND + "${CMAKE_COMMAND}" "-E" "${cmake_symlink_option}" + "${clang_headers_location}" + "${SWIFTSTATICLIB_DIR}/clang" + + CUSTOM_TARGET_NAME "symlink_clang_headers_static" + OUTPUT "${SWIFTSTATICLIB_DIR}/clang" + COMMENT "Symlinking Clang resource headers into ${SWIFTSTATICLIB_DIR}/clang") + + add_dependencies(copy_shim_headers symlink_clang_headers_static) +endif() + if(NOT SWIFT_BUILT_STANDALONE) if(TARGET clang-resource-headers) # LLVM > 8 set(clang_resource_headers clang-resource-headers) @@ -146,6 +183,12 @@ swift_install_in_component(FILES ${sources} DESTINATION "lib/swift/shims" COMPONENT stdlib) +if(SWIFT_BUILD_STATIC_STDLIB) + swift_install_in_component(FILES ${sources} + DESTINATION "lib/swift_static/shims" + COMPONENT stdlib) +endif() + # Install Clang headers under the Swift library so that an installed Swift's # module importer can find the compiler headers corresponding to its Clang. swift_install_in_component(DIRECTORY "${clang_headers_location}/" @@ -153,11 +196,26 @@ swift_install_in_component(DIRECTORY "${clang_headers_location}/" COMPONENT clang-builtin-headers PATTERN "*.h") +if(SWIFT_BUILD_STATIC_STDLIB) + swift_install_in_component(DIRECTORY "${clang_headers_location}/" + DESTINATION "lib/swift_static/clang" + COMPONENT clang-builtin-headers + PATTERN "*.h") +endif() + + swift_install_symlink_component(clang-resource-dir-symlink LINK_NAME clang TARGET ../clang/${CLANG_VERSION} DESTINATION "lib/swift") +if(SWIFT_BUILD_STATIC_STDLIB) + swift_install_symlink_component(clang-resource-dir-symlink + LINK_NAME clang + TARGET ../clang/${CLANG_VERSION} + DESTINATION "lib/swift_static") +endif() + # Possibly install Clang headers under Clang's resource directory in case we # need to use a different version of the headers than the installed Clang. This # should be used in conjunction with clang-resource-dir-symlink. diff --git a/test/Constraints/function_builder_diags.swift b/test/Constraints/function_builder_diags.swift index fae9cf22a3971..211108bf70ef6 100644 --- a/test/Constraints/function_builder_diags.swift +++ b/test/Constraints/function_builder_diags.swift @@ -606,6 +606,14 @@ struct MyView { } // expected-error {{expected identifier after '.' expression}} } + @TupleBuilder var invalidCaseWithoutDot: some P { + switch Optional.some(1) { + case none: 42 // expected-error {{cannot find 'none' in scope}} + case .some(let x): + 0 + } + } + @TupleBuilder var invalidConversion: Int { "" // expected-error {{cannot convert value of type 'String' to specified type 'Int'}} } diff --git a/test/Driver/coverage-prefix-map.swift b/test/Driver/coverage-prefix-map.swift new file mode 100644 index 0000000000000..fd2ff8a5cbc2c --- /dev/null +++ b/test/Driver/coverage-prefix-map.swift @@ -0,0 +1,9 @@ +// RUN: not %target-swiftc_driver -coverage-prefix-map old %s 2>&1 | %FileCheck %s -check-prefix CHECK-INVALID +// RUN: %target-swiftc_driver -### -coverage-prefix-map old=new %s 2>&1 | %FileCheck %s -check-prefix CHECK-SIMPLE +// RUN: %target-swiftc_driver -### -coverage-prefix-map old=n=ew %s 2>&1 | %FileCheck %s -check-prefix CHECK-COMPLEX +// RUN: %target-swiftc_driver -### -coverage-prefix-map old= %s 2>&1 | %FileCheck %s -check-prefix CHECK-EMPTY + +// CHECK-INVALID: error: invalid argument 'old' to -coverage-prefix-map +// CHECK-SIMPLE: coverage-prefix-map old=new +// CHECK-COMPLEX: coverage-prefix-map old=n=ew +// CHECK-EMPTY: coverage-prefix-map old= diff --git a/test/Driver/print_target_info.swift b/test/Driver/print_target_info.swift index 301473f984747..7dea336ec28b2 100644 --- a/test/Driver/print_target_info.swift +++ b/test/Driver/print_target_info.swift @@ -4,6 +4,10 @@ // RUN: %swift_driver -print-target-info -target x86_64-unknown-linux | %FileCheck -check-prefix CHECK-LINUX %s // RUN: %target-swift-frontend -print-target-info -target x86_64-unknown-linux | %FileCheck -check-prefix CHECK-LINUX %s +// RUN: %swift_driver -print-target-info -target x86_64-unknown-linux -static-executable | %FileCheck -check-prefix CHECK-LINUX-STATIC %s +// RUN: %swift_driver -print-target-info -target x86_64-unknown-linux -static-stdlib | %FileCheck -check-prefix CHECK-LINUX-STATIC %s +// RUN: %target-swift-frontend -print-target-info -target x86_64-unknown-linux -use-static-resource-dir | %FileCheck -check-prefix CHECK-LINUX-STATIC %s + // RUN: %swift_driver -print-target-info -target x86_64-apple-macosx10.15 -target-variant x86_64-apple-ios13-macabi | %FileCheck -check-prefix CHECK-ZIPPERED %s // RUN: %target-swift-frontend -print-target-info -target x86_64-apple-macosx10.15 -target-variant x86_64-apple-ios13-macabi | %FileCheck -check-prefix CHECK-ZIPPERED %s @@ -32,9 +36,22 @@ // CHECK-LINUX: "librariesRequireRPath": false // CHECK-LINUX: } +// CHECK-LINUX: "runtimeResourcePath": "{{.*}}lib{{(/|\\\\)}}swift" + // CHECK-LINUX-NOT: "targetVariant": +// CHECK-LINUX-STATIC: "target": { +// CHECK-LINUX-STATIC: "triple": "x86_64-unknown-linux", +// CHECK-LINUX-STATIC: "moduleTriple": "x86_64-unknown-linux", +// CHECK-LINUX-STATIC: "librariesRequireRPath": false +// CHECK-LINUX-STATIC: } + +// CHECK-LINUX-STATIC: "runtimeResourcePath": "{{.*}}lib{{(/|\\\\)}}swift_static" + +// CHECK-LINUX-STATIC-NOT: "targetVariant": + + // CHECK-ZIPPERED: "target": { // CHECK-ZIPPERED: "triple": "x86_64-apple-macosx10.15" // CHECK-ZIPPERED: "unversionedTriple": "x86_64-apple-macosx" diff --git a/test/IRGen/Inputs/local_extern.h b/test/IRGen/Inputs/local_extern.h new file mode 100644 index 0000000000000..de84f094bee45 --- /dev/null +++ b/test/IRGen/Inputs/local_extern.h @@ -0,0 +1,21 @@ +static inline int _no_prior_var() { + extern int var; + return var; +} + +static inline int _no_prior_func() { + extern int func(); + return func(); +} + +static int prior_var = 1; +static inline int _prior_var() { + extern int prior_var; + return prior_var; +} + +static inline int prior_func() { return 1; } +static inline int _prior_func() { + extern int prior_func(); + return prior_func(); +} diff --git a/test/IRGen/local_extern.swift b/test/IRGen/local_extern.swift new file mode 100644 index 0000000000000..06c9a3d5e94bd --- /dev/null +++ b/test/IRGen/local_extern.swift @@ -0,0 +1,10 @@ +// RUN: %target-swift-frontend -import-objc-header %S/Inputs/local_extern.h %s -emit-ir | %FileCheck %s +// CHECK: @var = external {{(dso_local )?}}global i32 +// CHECK: @prior_var = internal global i32 +// CHECK: declare {{(dso_local )?}}i32 @func +// CHECK: define internal i32 @prior_func + +print("\(_no_prior_var())") +print("\(_no_prior_func())") +print("\(_prior_var())") +print("\(_prior_func())") diff --git a/test/Interop/C/function/Inputs/emit-called-inline-function.h b/test/Interop/C/function/Inputs/emit-called-inline-function.h new file mode 100644 index 0000000000000..437d3b8bac6c1 --- /dev/null +++ b/test/Interop/C/function/Inputs/emit-called-inline-function.h @@ -0,0 +1,49 @@ +#ifdef __cplusplus +#define INLINE inline +#else +// When compiling as C, make the functions `static inline`. This is the flavor +// of inline functions for which we require the behavior checked by this test. +// Non-static C inline functions don't require Swift to emit LLVM IR for them +// because the idea is that there will we one `.c` file that declares them +// `extern inline`, causing an out-of-line definition to be emitted to the +// corresponding .o file. +#define INLINE static inline +#endif + +INLINE int notCalled() { + return 42; +} + +INLINE int calledTransitively() { + return 42; +} + +#ifdef __cplusplus +class C { + public: + int memberFunctionCalledTransitively() { + return 42; + } +}; + +inline int calledTransitivelyFromVarInit() { + return 42; +} + +inline int varUsedFromSwift = calledTransitivelyFromVarInit(); +#else +// C only allows constant initializers for variables with static storage +// duration, so there's no way to initialize this with the result of a call to +// an inline method. Just provide _some_ definition of `varImportedToSwift` so +// we can import it in the test. +static int varUsedFromSwift = 42; +#endif + +INLINE int calledFromSwift() { +#ifdef __cplusplus + C c; + return calledTransitively() + c.memberFunctionCalledTransitively(); +#else + return calledTransitively(); +#endif +} diff --git a/test/Interop/C/function/Inputs/module.modulemap b/test/Interop/C/function/Inputs/module.modulemap new file mode 100644 index 0000000000000..77c866f587b72 --- /dev/null +++ b/test/Interop/C/function/Inputs/module.modulemap @@ -0,0 +1,4 @@ +module EmitCalledInlineFunction { + header "emit-called-inline-function.h" + export * +} diff --git a/test/Interop/C/function/emit-called-inline-function-irgen.swift b/test/Interop/C/function/emit-called-inline-function-irgen.swift new file mode 100644 index 0000000000000..851d855640d96 --- /dev/null +++ b/test/Interop/C/function/emit-called-inline-function-irgen.swift @@ -0,0 +1,23 @@ +// Test that we emit LLVM IR for inline functions that are called directly or +// transitively from Swift. +// +// Test that we don't emit LLVM IR for inline functions that are not called from +// Swift. + +// RUN: %empty-directory(%t) +// RUN: %target-swift-frontend %s -I %S/Inputs -Xcc -std=c99 -emit-ir -o - | %FileCheck %s -check-prefix C99 --implicit-check-not notCalled +// RUN: %target-swift-frontend %s -I %S/Inputs -enable-cxx-interop -emit-ir -o - | %FileCheck %s -check-prefix CXX --implicit-check-not notCalled + +import EmitCalledInlineFunction + +// C99-DAG: define internal i32 @calledFromSwift() +// C99-DAG: define internal i32 @calledTransitively() + +// CXX-DAG: define linkonce_odr{{( dso_local)?}} i32 @{{_Z15calledFromSwiftv|"\?calledFromSwift@@YAHXZ"}}() +// CXX-DAG: define linkonce_odr{{( dso_local)?}} i32 @{{_Z18calledTransitivelyv|"\?calledTransitively@@YAHXZ"}}() +// CXX-DAG: define linkonce_odr{{( dso_local)?}} i32 @{{_ZN1C32memberFunctionCalledTransitivelyEv|"\?memberFunctionCalledTransitively@C@@QEAAHXZ"}}(%class.C* %this) +// CXX-DAG: define linkonce_odr{{( dso_local)?}} i32 @{{_Z29calledTransitivelyFromVarInitv|"\?calledTransitivelyFromVarInit@@YAHXZ"}}() + +calledFromSwift() + +let _ = varUsedFromSwift diff --git a/test/Profiler/Inputs/coverage_num_threads1.swift b/test/Profiler/Inputs/coverage_num_threads1.swift new file mode 100644 index 0000000000000..6ca641732e7e1 --- /dev/null +++ b/test/Profiler/Inputs/coverage_num_threads1.swift @@ -0,0 +1 @@ +func func1() {} diff --git a/test/Profiler/Inputs/coverage_num_threads2.swift b/test/Profiler/Inputs/coverage_num_threads2.swift new file mode 100644 index 0000000000000..639ea1b4ad4b7 --- /dev/null +++ b/test/Profiler/Inputs/coverage_num_threads2.swift @@ -0,0 +1 @@ +func func2() {} diff --git a/test/Profiler/coverage_num_threads.swift b/test/Profiler/coverage_num_threads.swift new file mode 100644 index 0000000000000..12156483c079e --- /dev/null +++ b/test/Profiler/coverage_num_threads.swift @@ -0,0 +1,13 @@ +// RUN: %target-swift-frontend -profile-generate -profile-coverage-mapping -num-threads 0 -emit-ir %S/Inputs/coverage_num_threads1.swift | %FileCheck %s -check-prefix=SINGLE-SOURCE --implicit-check-not="llvm_coverage_mapping =" + +// SINGLE-SOURCE: llvm_coverage_mapping = + +// RUN: %target-swift-frontend -profile-generate -profile-coverage-mapping -num-threads 0 -emit-ir %S/Inputs/coverage_num_threads1.swift %S/Inputs/coverage_num_threads2.swift | %FileCheck %s -check-prefix=SINGLE-OBJECT --implicit-check-not="llvm_coverage_mapping =" + +// SINGLE-OBJECT: llvm_coverage_mapping = + +// Using 1 goes down the multithreaded codepath but only operates with a single thread to work around an issue on Windows where the output of both IR modules is interleaved and therefore the output is invalid +// RUN: %target-swift-frontend -profile-generate -profile-coverage-mapping -num-threads 1 -emit-ir %S/Inputs/coverage_num_threads1.swift %S/Inputs/coverage_num_threads2.swift | %FileCheck %s -check-prefix=MULTIPLE-OBJECTS --implicit-check-not="llvm_coverage_mapping =" + +// MULTIPLE-OBJECTS: llvm_coverage_mapping = +// MULTIPLE-OBJECTS: llvm_coverage_mapping = diff --git a/test/Profiler/coverage_relative_path.swift b/test/Profiler/coverage_relative_path.swift new file mode 100644 index 0000000000000..2e5683b382abf --- /dev/null +++ b/test/Profiler/coverage_relative_path.swift @@ -0,0 +1,16 @@ +// %s expands to an absolute path, so to test relative paths we need to create a +// clean directory, put the source there, and cd into it. +// RUN: rm -rf %t +// RUN: mkdir -p %t/foo/bar/baz +// RUN: echo "func coverage() {}" > %t/foo/bar/baz/coverage_relative_path.swift +// RUN: cd %t/foo/bar + +// RUN: %target-swift-frontend -profile-generate -profile-coverage-mapping -Xllvm -enable-name-compression=false -emit-ir %/t/foo/bar/baz/coverage_relative_path.swift | %FileCheck -check-prefix=ABSOLUTE %s +// +// ABSOLUTE: @__llvm_coverage_mapping = {{.*"\\01.*foo.*bar.*baz.*coverage_relative_path\.swift}} + +// RUN: %target-swift-frontend -profile-generate -profile-coverage-mapping -Xllvm -enable-name-compression=false -coverage-prefix-map %/t/foo/bar=. -emit-ir %/t/foo/bar/baz/coverage_relative_path.swift | %FileCheck -check-prefix=RELATIVE %s +// +// RELATIVE: @__llvm_coverage_mapping = {{.*"\\01[^/]*}}.{{/|\\}}baz{{.*coverage_relative_path\.swift}} + +func coverage() {} diff --git a/test/SILGen/Inputs/replace_opaque_type_public_assoc_type_m.swift b/test/SILGen/Inputs/replace_opaque_type_public_assoc_type_m.swift new file mode 100644 index 0000000000000..c2120db7cb831 --- /dev/null +++ b/test/SILGen/Inputs/replace_opaque_type_public_assoc_type_m.swift @@ -0,0 +1,11 @@ +public protocol Gesture { + associatedtype Body: Gesture + var body: Body { get } + + associatedtype Value + var value: Value { get } +} + +extension Gesture { + public var value: Body.Value { return body.value } +} diff --git a/test/SILGen/replace_opaque_type_public_assoc_type.swift b/test/SILGen/replace_opaque_type_public_assoc_type.swift new file mode 100644 index 0000000000000..c256b3237748c --- /dev/null +++ b/test/SILGen/replace_opaque_type_public_assoc_type.swift @@ -0,0 +1,14 @@ +// RUN: %empty-directory(%t) +// RUN: %target-swift-frontend -disable-availability-checking -emit-module-path %t/replace_opaque_type_public_assoc_type_m.swiftmodule %S/Inputs/replace_opaque_type_public_assoc_type_m.swift +// RUN: %target-swift-emit-silgen -disable-availability-checking -I %t %s -verify + +import replace_opaque_type_public_assoc_type_m + +struct PiggyBack: Gesture { + var action: () -> Void + + var body: some Gesture { + action() + return self + } +} diff --git a/test/SILOptimizer/sil_combine.sil b/test/SILOptimizer/sil_combine.sil index 0b28ba548b130..ab9ca8c989b75 100644 --- a/test/SILOptimizer/sil_combine.sil +++ b/test/SILOptimizer/sil_combine.sil @@ -3189,6 +3189,33 @@ bb0(%0 : $VV): return %26 : $() } +sil @any_to_object : $@convention(thin) <τ_0_0> (@in_guaranteed τ_0_0) -> @owned AnyObject + +// CHECK-LABEL: sil @dont_crash_when_propagating_existentials +// CHECK: [[EM:%[0-9]+]] = init_existential_metatype %0 +// CHECK: [[S:%[0-9]+]] = alloc_stack $Any +// CHECK: [[M:%[0-9]+]] = open_existential_metatype [[EM]] +// CHECK: [[E:%[0-9]+]] = init_existential_addr [[S]] +// CHECK: store [[M]] to [[E]] +// CHECK: apply {{%[0-9]+}}<(@opened("5F99B72C-EC40-11EA-9534-8C8590A6A134") AnyObject).Type>([[E]]) +// CHECK: } // end sil function 'dont_crash_when_propagating_existentials' +sil @dont_crash_when_propagating_existentials : $@convention(thin) () -> @owned AnyObject { +bb0: + %0 = metatype $@thick C.Type + %1 = init_existential_metatype %0 : $@thick C.Type, $@thick AnyObject.Type + %3 = alloc_stack $Any, let, name "object" + %4 = open_existential_metatype %1 : $@thick AnyObject.Type to $@thick (@opened("5F99B72C-EC40-11EA-9534-8C8590A6A134") AnyObject).Type + %5 = init_existential_addr %3 : $*Any, $(@opened("5F99B72C-EC40-11EA-9534-8C8590A6A134") AnyObject).Type + store %4 to %5 : $*@thick (@opened("5F99B72C-EC40-11EA-9534-8C8590A6A134") AnyObject).Type + %7 = open_existential_addr immutable_access %3 : $*Any to $*@opened("5F9F1B04-EC40-11EA-9534-8C8590A6A134") Any + %8 = function_ref @any_to_object : $@convention(thin) <τ_0_0> (@in_guaranteed τ_0_0) -> @owned AnyObject + %9 = apply %8<@opened("5F9F1B04-EC40-11EA-9534-8C8590A6A134") Any>(%7) : $@convention(thin) <τ_0_0> (@in_guaranteed τ_0_0) -> @owned AnyObject + destroy_addr %3 : $*Any + dealloc_stack %3 : $*Any + return %9 : $AnyObject +} + + // CHECK-LABEL: sil @remove_unused_alloc_ref // CHECK-NEXT: bb0 // CHECK-NEXT: %0 = tuple () diff --git a/test/attr/attr_availability_canonical_macos_version.swift b/test/attr/attr_availability_canonical_macos_version.swift index e512a97e45465..071cf6ae49de7 100644 --- a/test/attr/attr_availability_canonical_macos_version.swift +++ b/test/attr/attr_availability_canonical_macos_version.swift @@ -1,8 +1,5 @@ // RUN: %swift -typecheck -verify -parse-stdlib -module-name Swift -target x86_64-apple-macosx11.0 %s -// REQUIRES: rdar66693249 - - @available(OSX, introduced: 10.5, deprecated: 10.8, obsoleted: 11.0, message: "you don't want to do that anyway") func obsoletedIn11() { } diff --git a/tools/driver/modulewrap_main.cpp b/tools/driver/modulewrap_main.cpp index 187893ec72301..510cf5d3edabf 100644 --- a/tools/driver/modulewrap_main.cpp +++ b/tools/driver/modulewrap_main.cpp @@ -44,6 +44,7 @@ class ModuleWrapInvocation { std::string OutputFilename = "-"; llvm::Triple TargetTriple; std::vector InputFilenames; + bool UseSharedResourceFolder = true; public: bool hasSingleInput() const { return InputFilenames.size() == 1; } @@ -60,6 +61,8 @@ class ModuleWrapInvocation { const std::vector &getInputFilenames() { return InputFilenames; } llvm::Triple &getTargetTriple() { return TargetTriple; } + bool useSharedResourceFolder() { return UseSharedResourceFolder; } + int parseArgs(llvm::ArrayRef Args, DiagnosticEngine &Diags) { using namespace options; @@ -111,6 +114,13 @@ class ModuleWrapInvocation { OutputFilename = A->getValue(); } + if (ParsedArgs.hasFlag(OPT_static_executable, OPT_no_static_executable, + false) || + ParsedArgs.hasFlag(OPT_static_stdlib, OPT_no_static_stdlib, false) || + ParsedArgs.hasArg(OPT_static)) { + UseSharedResourceFolder = false; + } + return 0; } }; @@ -159,7 +169,8 @@ int modulewrap_main(ArrayRef Args, const char *Argv0, SearchPathOptions SearchPathOpts; SmallString<128> RuntimeResourcePath; CompilerInvocation::computeRuntimeResourcePathFromExecutablePath( - MainExecutablePath, RuntimeResourcePath); + MainExecutablePath, Invocation.useSharedResourceFolder(), + RuntimeResourcePath); SearchPathOpts.RuntimeResourcePath = std::string(RuntimeResourcePath.str()); SourceManager SrcMgr; diff --git a/utils/build-presets.ini b/utils/build-presets.ini index a317a03314a10..70a3d5125b0ee 100644 --- a/utils/build-presets.ini +++ b/utils/build-presets.ini @@ -1214,6 +1214,9 @@ compiler-vendor=apple dash-dash +# Cross compile for Apple Silicon +cross-compile-hosts=macosx-arm64 + lldb-no-debugserver lldb-use-system-debugserver lldb-build-type=Release @@ -1221,6 +1224,11 @@ verbose-build build-ninja build-swift-stdlib-unittest-extra +# When producing a package, don't copy the Swift Resource/ directory. +# This is mainly a space optimization. +extra-cmake-options= + -DLLDB_FRAMEWORK_COPY_SWIFT_RESOURCES=0 + install-swift install-lldb install-llbuild @@ -1282,6 +1290,8 @@ stress-test dash-dash lldb-test-swift-only +# SKIP LLDB TESTS (67923799) +skip-test-lldb # Path to the .tar.gz package we would create. installable-package=%(installable_package)s @@ -2379,21 +2389,25 @@ swift-install-components=autolink-driver;compiler;clang-builtin-headers;stdlib;s mixin-preset=source_compat_suite_macos_base debug assertions +cross-compile-hosts=macosx-arm64 [preset: source_compat_suite_macos_RA] mixin-preset=source_compat_suite_macos_base release assertions +cross-compile-hosts=macosx-arm64 [preset: source_compat_suite_macos_R] mixin-preset=source_compat_suite_macos_base release no-assertions +cross-compile-hosts=macosx-arm64 [preset: source_compat_suite_macos_D] mixin-preset=source_compat_suite_macos_base debug no-assertions +cross-compile-hosts=macosx-arm64 [preset: source_compat_suite_linux_DA] mixin-preset=source_compat_suite_linux_base diff --git a/utils/build-script b/utils/build-script index 231940f8fcd33..1e1845f39b643 100755 --- a/utils/build-script +++ b/utils/build-script @@ -934,6 +934,9 @@ class BuildScriptInvocation(object): for product_class in impl_product_classes: self._execute_install_action(host_target, product_class) + # Core Lipo... + self._execute_merged_host_lipo_core_action() + # Non-build-script-impl products... # Note: currently only supports building for the host. for host_target in [self.args.host_target]: @@ -1001,6 +1004,9 @@ class BuildScriptInvocation(object): def _execute_merged_host_lipo_action(self): self._execute_action("merged-hosts-lipo") + def _execute_merged_host_lipo_core_action(self): + self._execute_action("merged-hosts-lipo-core") + def _execute_action(self, action_name): shell.call_without_sleeping( [BUILD_SCRIPT_IMPL_PATH] + self.impl_args + diff --git a/utils/build-script-impl b/utils/build-script-impl index c39e115c49318..3ebea70eaa2dc 100755 --- a/utils/build-script-impl +++ b/utils/build-script-impl @@ -453,6 +453,7 @@ function set_build_options_for_host() { swift_cmake_options=() cmark_cmake_options=() lldb_cmake_options=() + llbuild_cmake_options=() SWIFT_HOST_VARIANT= SWIFT_HOST_VARIANT_SDK= SWIFT_HOST_VARIANT_ARCH= @@ -669,6 +670,7 @@ function set_build_options_for_host() { -DCMAKE_CXX_FLAGS="$(cmark_c_flags ${host})" -DCMAKE_OSX_SYSROOT:PATH="${cmake_os_sysroot}" -DCMAKE_OSX_DEPLOYMENT_TARGET="${cmake_osx_deployment_target}" + -DCMAKE_OSX_ARCHITECTURES="${architecture}" ) llvm_cmake_options=( -DCMAKE_OSX_DEPLOYMENT_TARGET:STRING="${cmake_osx_deployment_target}" @@ -678,6 +680,7 @@ function set_build_options_for_host() { -DCOMPILER_RT_ENABLE_TVOS:BOOL=FALSE -DSANITIZER_MIN_OSX_VERSION="${cmake_osx_deployment_target}" -DLLVM_ENABLE_MODULES:BOOL="$(true_false ${LLVM_ENABLE_MODULES})" + -DCMAKE_OSX_ARCHITECTURES="${architecture}" ) if [[ $(is_llvm_lto_enabled) == "TRUE" ]]; then llvm_cmake_options+=( @@ -706,6 +709,13 @@ function set_build_options_for_host() { # in the compiler checks CMake performs -DCMAKE_OSX_ARCHITECTURES="${architecture}" ) + + lldb_cmake_options+=( + -DCMAKE_OSX_ARCHITECTURES="${architecture}" + ) + llbuild_cmake_options+=( + -DCMAKE_OSX_ARCHITECTURES="${architecture}" + ) ;; esac @@ -2015,6 +2025,7 @@ for host in "${ALL_HOSTS[@]}"; do llbuild) cmake_options=( "${cmake_options[@]}" + "${llbuild_cmake_options[@]}" -DCMAKE_BUILD_TYPE:STRING="${LLBUILD_BUILD_TYPE}" -DCMAKE_INSTALL_PREFIX:PATH="$(get_host_install_prefix ${host})" @@ -2456,13 +2467,15 @@ for host in "${ALL_HOSTS[@]}"; do executable_target= results_targets= if ! [[ "${SKIP_TEST_SWIFT}" ]]; then - executable_target=SwiftUnitTests - results_targets=("${SWIFT_TEST_TARGETS[@]}") - if [[ "${STRESS_TEST_SOURCEKIT}" ]]; then - results_targets=( - "${results_targets[@]}" - stress-SourceKit - ) + if ! [[ $(is_cross_tools_host ${host}) ]] ; then + executable_target=SwiftUnitTests + results_targets=("${SWIFT_TEST_TARGETS[@]}") + if [[ "${STRESS_TEST_SOURCEKIT}" ]]; then + results_targets=( + "${results_targets[@]}" + stress-SourceKit + ) + fi fi fi if ! [[ "${SKIP_TEST_BENCHMARKS}" ]]; then @@ -2479,6 +2492,10 @@ for host in "${ALL_HOSTS[@]}"; do if [[ "${SKIP_TEST_LLDB}" ]]; then continue fi + if [[ $(is_cross_tools_host ${host}) ]]; then + echo "--- Can't execute tests for ${host}, skipping... ---" + continue + fi llvm_build_dir=$(build_directory ${host} llvm) lldb_build_dir=$(build_directory ${host} lldb) results_dir="${lldb_build_dir}/test-results" @@ -2781,8 +2798,12 @@ for host in "${ALL_HOSTS[@]}"; do fi if [[ "${LLVM_INSTALL_COMPONENTS}" == "all" ]]; then INSTALL_TARGETS=install - else - INSTALL_TARGETS=install-$(echo ${LLVM_INSTALL_COMPONENTS} | sed -E 's/;/ install-/g') + elif [[ -n "${LLVM_INSTALL_COMPONENTS}" ]] ; then + if [[ $(is_cross_tools_host ${host}) && "${LLVM_INSTALL_COMPONENTS}" == *"compiler-rt"* ]]; then + INSTALL_TARGETS=install-$(echo ${LLVM_INSTALL_COMPONENTS} | sed -E 's/compiler-rt;//g' |sed -E 's/;/ install-/g') + else + INSTALL_TARGETS=install-$(echo ${LLVM_INSTALL_COMPONENTS} | sed -E 's/;/ install-/g') + fi fi ;; libcxx) @@ -3009,11 +3030,7 @@ function build_and_test_installable_package() { local host_install_destdir="$(get_host_install_destdir ${host})" local host_install_prefix="$(get_host_install_prefix ${host})" - if [[ $(has_cross_compile_hosts) ]]; then - package_for_host="${INSTALLABLE_PACKAGE}-${host}" - else - package_for_host="${INSTALLABLE_PACKAGE}" - fi + package_for_host="${INSTALLABLE_PACKAGE}" echo "--- Creating installable package ---" echo "-- Package file: ${package_for_host} --" @@ -3083,7 +3100,7 @@ function build_and_test_installable_package() { PKG_TESTS_SANDBOX_PARENT="$(build_directory swift_package_sandbox_${host} none)" PKG_TESTS_TEMPS="${PKG_TESTS_SANDBOX_PARENT}"/"tests" - if [[ "${host}" == "macosx-"* ]] ; then + if [[ "${host}" == "macosx-"* ]] || [[ "${host}" == "merged-hosts" ]]; then PKG_TESTS_SANDBOX="${PKG_TESTS_SANDBOX_PARENT}"/"${TOOLCHAIN_PREFIX}" else # Linux PKG_TESTS_SANDBOX="${PKG_TESTS_SANDBOX_PARENT}" @@ -3124,7 +3141,7 @@ if [[ ${#LIPO_SRC_DIRS[@]} -gt 0 ]]; then # This is from multiple hosts; Which host should we say it is? # Let's call it 'merged-hosts' so that we can identify it. - if [[ $(should_execute_action "${mergedHost}-lipo") ]]; then + if [[ $(should_execute_action "${mergedHost}-lipo") || $(should_execute_action "${mergedHost}-lipo-core") ]]; then # Allow passing lipo with --host-lipo if [[ -z "${HOST_LIPO}" ]] ; then LIPO_PATH=$(xcrun_find_tool lipo) @@ -3133,8 +3150,10 @@ if [[ ${#LIPO_SRC_DIRS[@]} -gt 0 ]]; then fi call "${SWIFT_SOURCE_DIR}"/utils/recursive-lipo --lipo=${LIPO_PATH} --copy-subdirs="$(get_host_install_prefix ${host})lib/swift $(get_host_install_prefix ${host})lib/swift_static" --destination="$(get_host_install_destdir ${mergedHost})" ${LIPO_SRC_DIRS[@]} - # Build and test the lipo-ed package. - build_and_test_installable_package ${mergedHost} + if [[ $(should_execute_action "${mergedHost}-lipo") ]]; then + # Build and test the lipo-ed package. + build_and_test_installable_package ${mergedHost} + fi fi fi # END diff --git a/utils/recursive-lipo b/utils/recursive-lipo index 056b5f3576ef6..df3d302e651fd 100755 --- a/utils/recursive-lipo +++ b/utils/recursive-lipo @@ -63,6 +63,9 @@ def merge_lipo_files(src_root_dirs, file_list, copy_verbatim_subpaths, if all([os.path.islink(item) for item in file_paths]): # It's a symlink in all found instances, copy the link. print("-- Creating symlink %s" % dest_path) + # Remove symlink if it already exists + if os.path.islink(dest_path): + os.remove(dest_path) os.symlink(os.readlink(file_paths[0]), dest_path) elif all([os.path.isdir(item) for item in file_paths]): # It's a subdir in all found instances. diff --git a/utils/swift_build_support/swift_build_support/products/benchmarks.py b/utils/swift_build_support/swift_build_support/products/benchmarks.py index 65232f8060fdc..c36475ff62073 100644 --- a/utils/swift_build_support/swift_build_support/products/benchmarks.py +++ b/utils/swift_build_support/swift_build_support/products/benchmarks.py @@ -14,6 +14,7 @@ import platform from . import product +from . import swiftpm from .. import shell from .. import targets @@ -59,7 +60,9 @@ def install(self, host_target): def run_build_script_helper(host_target, product, args): - toolchain_path = args.install_destdir + toolchain_path = swiftpm.SwiftPM.get_install_destdir(args, + host_target, + product.build_dir) if platform.system() == 'Darwin': # The prefix is an absolute path, so concatenate without os.path. toolchain_path += \ diff --git a/utils/swift_build_support/swift_build_support/products/indexstoredb.py b/utils/swift_build_support/swift_build_support/products/indexstoredb.py index 6bd7d2b6f566f..0cce0c376d486 100644 --- a/utils/swift_build_support/swift_build_support/products/indexstoredb.py +++ b/utils/swift_build_support/swift_build_support/products/indexstoredb.py @@ -13,6 +13,7 @@ import os from . import product +from . import swiftpm from .. import shell from .. import targets @@ -51,7 +52,12 @@ def run_build_script_helper(action, host_target, product, args, script_path = os.path.join( product.source_dir, 'Utilities', 'build-script-helper.py') - toolchain_path = targets.toolchain_path(args.install_destdir, + install_destdir = args.install_destdir + if swiftpm.SwiftPM.has_cross_compile_hosts(args): + install_destdir = swiftpm.SwiftPM.get_install_destdir(args, + host_target, + product.build_dir) + toolchain_path = targets.toolchain_path(install_destdir, args.install_prefix) is_release = product.is_release() configuration = 'release' if is_release else 'debug' diff --git a/utils/swift_build_support/swift_build_support/products/product.py b/utils/swift_build_support/swift_build_support/products/product.py index 6837e563c91ae..6180f9c1139a7 100644 --- a/utils/swift_build_support/swift_build_support/products/product.py +++ b/utils/swift_build_support/swift_build_support/products/product.py @@ -11,6 +11,7 @@ # ---------------------------------------------------------------------------- import abc +import os from .. import cmake from .. import targets @@ -136,13 +137,17 @@ def is_release(self): """ return is_release_variant(self.args.build_variant) - def install_toolchain_path(self): + def install_toolchain_path(self, host_target): """toolchain_path() -> string Returns the path to the toolchain that is being created as part of this build. """ - return targets.toolchain_path(self.args.install_destdir, + install_destdir = self.args.install_destdir + if self.args.cross_compile_hosts: + build_root = os.path.dirname(self.build_dir) + install_destdir = '%s/intermediate-install/%s' % (build_root, host_target) + return targets.toolchain_path(install_destdir, self.args.install_prefix) diff --git a/utils/swift_build_support/swift_build_support/products/skstresstester.py b/utils/swift_build_support/swift_build_support/products/skstresstester.py index 1db633c553234..929e761c98602 100644 --- a/utils/swift_build_support/swift_build_support/products/skstresstester.py +++ b/utils/swift_build_support/swift_build_support/products/skstresstester.py @@ -17,6 +17,7 @@ from build_swift.build_swift.constants import MULTIROOT_DATA_FILE_PATH from . import product +from . import swiftpm from .. import shell @@ -40,7 +41,7 @@ def is_swiftpm_unified_build_product(cls): def package_name(self): return 'SourceKitStressTester' - def run_build_script_helper(self, action, additional_params=[]): + def run_build_script_helper(self, action, host_target, additional_params=[]): script_path = os.path.join( self.source_dir, 'build-script-helper.py') @@ -50,7 +51,7 @@ def run_build_script_helper(self, action, additional_params=[]): script_path, action, '--package-dir', self.package_name(), - '--toolchain', self.install_toolchain_path(), + '--toolchain', self.install_toolchain_path(host_target), '--config', configuration, '--build-dir', self.build_dir, '--multiroot-data-file', MULTIROOT_DATA_FILE_PATH, @@ -74,19 +75,22 @@ def build(self, host_target): "than Darwin".format( product=self.package_name())) - self.run_build_script_helper('build') + self.run_build_script_helper('build', host_target) def should_test(self, host_target): return self.args.test_skstresstester def test(self, host_target): - self.run_build_script_helper('test') + self.run_build_script_helper('test', host_target) def should_install(self, host_target): return self.args.install_skstresstester def install(self, host_target): - install_prefix = self.args.install_destdir + self.args.install_prefix - self.run_build_script_helper('install', [ + install_destdir = swiftpm.SwiftPM.get_install_destdir(self.args, + host_target, + self.build_dir) + install_prefix = install_destdir + self.args.install_prefix + self.run_build_script_helper('install', host_target, [ '--prefix', install_prefix ]) diff --git a/utils/swift_build_support/swift_build_support/products/swiftpm.py b/utils/swift_build_support/swift_build_support/products/swiftpm.py index 3fe2c4be3e80b..563cd46ee77f2 100644 --- a/utils/swift_build_support/swift_build_support/products/swiftpm.py +++ b/utils/swift_build_support/swift_build_support/products/swiftpm.py @@ -31,7 +31,7 @@ def should_build(self, host_target): def run_bootstrap_script(self, action, host_target, additional_params=[]): script_path = os.path.join( self.source_dir, 'Utilities', 'bootstrap') - toolchain_path = self.install_toolchain_path() + toolchain_path = self.install_toolchain_path(host_target) swiftc = os.path.join(toolchain_path, "bin", "swiftc") # FIXME: We require llbuild build directory in order to build. Is @@ -53,6 +53,13 @@ def run_bootstrap_script(self, action, host_target, additional_params=[]): "--build-dir", self.build_dir, "--llbuild-build-dir", llbuild_build_dir ] + + # Pass Cross compile host info + if self.has_cross_compile_hosts(self.args): + helper_cmd += ['--cross-compile-hosts'] + for cross_compile_host in self.args.cross_compile_hosts: + helper_cmd += [cross_compile_host] + helper_cmd.extend(additional_params) shell.call(helper_cmd) @@ -69,8 +76,24 @@ def test(self, host_target): def should_install(self, host_target): return self.args.install_swiftpm + @classmethod + def has_cross_compile_hosts(self, args): + return args.cross_compile_hosts + + @classmethod + def get_install_destdir(self, args, host_target, build_dir): + install_destdir = args.install_destdir + if self.has_cross_compile_hosts(args): + build_root = os.path.dirname(build_dir) + install_destdir = '%s/intermediate-install/%s' % (build_root, host_target) + return install_destdir + def install(self, host_target): - install_prefix = self.args.install_destdir + self.args.install_prefix + install_destdir = self.get_install_destdir(self.args, + host_target, + self.build_dir) + install_prefix = install_destdir + self.args.install_prefix + self.run_bootstrap_script('install', host_target, [ '--prefix', install_prefix ]) diff --git a/utils/swift_build_support/swift_build_support/products/swiftsyntax.py b/utils/swift_build_support/swift_build_support/products/swiftsyntax.py index 6ed06c5b6ff9a..f8d6526aebb0c 100644 --- a/utils/swift_build_support/swift_build_support/products/swiftsyntax.py +++ b/utils/swift_build_support/swift_build_support/products/swiftsyntax.py @@ -45,7 +45,7 @@ def run_swiftsyntax_build_script(self, target, additional_params=[]): script_path, '--build-dir', self.build_dir, '--multiroot-data-file', MULTIROOT_DATA_FILE_PATH, - '--toolchain', self.install_toolchain_path(), + '--toolchain', self.install_toolchain_path(target), '--filecheck-exec', os.path.join(llvm_build_dir, 'bin', 'FileCheck'), ] diff --git a/utils/webassembly/build-toolchain.sh b/utils/webassembly/build-toolchain.sh index 3bb0231ddb5ae..0129a373ac71c 100755 --- a/utils/webassembly/build-toolchain.sh +++ b/utils/webassembly/build-toolchain.sh @@ -85,5 +85,10 @@ rsync -v -a $SOURCE_PATH/install/$TOOLCHAIN_NAME/usr/lib/ $HOST_TOOLCHAIN_SDK/us $UTILS_PATH/build-foundation.sh $HOST_TOOLCHAIN_SDK $UTILS_PATH/build-xctest.sh $HOST_TOOLCHAIN_SDK +# Cleanup build directory on CI +if [[ -z "${CI}" ]]; then + rm -rf $SOURCE_PATH/build/Ninja-ReleaseAssert/ +fi + cd $HOST_TOOLCHAIN_DESTDIR tar cfz $PACKAGE_ARTIFACT $TOOLCHAIN_NAME