diff --git a/include/swift/AST/ASTContext.h b/include/swift/AST/ASTContext.h index 47c712db6f993..aa864037e91fb 100644 --- a/include/swift/AST/ASTContext.h +++ b/include/swift/AST/ASTContext.h @@ -1093,10 +1093,6 @@ class ASTContext final { /// Retrieve the module interface checker associated with this AST context. ModuleInterfaceChecker *getModuleInterfaceChecker() const; - /// Compute the extra implicit framework search paths on Apple platforms: - /// $SDKROOT/System/Library/Frameworks/ and $SDKROOT/Library/Frameworks/. - std::vector getDarwinImplicitFrameworkSearchPaths() const; - /// Load extensions to the given nominal type from the external /// module loaders. /// diff --git a/include/swift/AST/SearchPathOptions.h b/include/swift/AST/SearchPathOptions.h index 1156288955327..0122d13fba2cc 100644 --- a/include/swift/AST/SearchPathOptions.h +++ b/include/swift/AST/SearchPathOptions.h @@ -35,7 +35,7 @@ namespace swift { enum class ModuleSearchPathKind { Import, Framework, - DarwinImplicitFramework, + ImplicitFramework, RuntimeLibrary, }; @@ -356,12 +356,8 @@ class SearchPathOptions { /// When on Darwin the framework paths that are implicitly imported. /// $SDKROOT/System/Library/Frameworks/ and $SDKROOT/Library/Frameworks/. /// - /// On non-Darwin platforms these are populated, but ignored. - /// - /// Computed when the SDK path is set and cached so we can reference the - /// Darwin implicit framework search paths as \c StringRef from - /// \c ModuleSearchPath. - std::vector DarwinImplicitFrameworkSearchPaths; + /// Must be modified through setter to keep \c Lookup in sync. + std::vector ImplicitFrameworkSearchPaths; /// Compiler plugin library search paths. std::vector CompilerPluginLibraryPaths; @@ -401,21 +397,6 @@ class SearchPathOptions { void setSDKPath(std::string NewSDKPath) { SDKPath = NewSDKPath; - - // Compute Darwin implicit framework search paths. - SmallString<128> systemFrameworksScratch(NewSDKPath); - llvm::sys::path::append(systemFrameworksScratch, "System", "Library", - "Frameworks"); - SmallString<128> systemSubFrameworksScratch(NewSDKPath); - llvm::sys::path::append(systemSubFrameworksScratch, "System", "Library", - "SubFrameworks"); - SmallString<128> frameworksScratch(NewSDKPath); - llvm::sys::path::append(frameworksScratch, "Library", "Frameworks"); - DarwinImplicitFrameworkSearchPaths = {systemFrameworksScratch.str().str(), - systemSubFrameworksScratch.str().str(), - frameworksScratch.str().str()}; - - Lookup.searchPathsDidChange(); } /// Retrieves the corresponding parent platform path for the SDK, or @@ -470,8 +451,14 @@ class SearchPathOptions { /// The extra implicit framework search paths on Apple platforms: /// $SDKROOT/System/Library/Frameworks/ and $SDKROOT/Library/Frameworks/. - ArrayRef getDarwinImplicitFrameworkSearchPaths() const { - return DarwinImplicitFrameworkSearchPaths; + ArrayRef getImplicitFrameworkSearchPaths() const { + return ImplicitFrameworkSearchPaths; + } + + void setImplicitFrameworkSearchPaths( + std::vector NewImplicitFrameworkSearchPaths) { + ImplicitFrameworkSearchPaths = NewImplicitFrameworkSearchPaths; + Lookup.searchPathsDidChange(); } ArrayRef getRuntimeLibraryImportPaths() const { @@ -505,11 +492,11 @@ class SearchPathOptions { /// Path to in-process plugin server shared library. std::string InProcessPluginServerPath; - /// Don't look in for compiler-provided modules. - bool SkipRuntimeLibraryImportPaths = false; + /// Don't automatically add any import paths. + bool SkipAllImplicitImportPaths = false; - /// Don't include SDK paths in the RuntimeLibraryImportPaths - bool ExcludeSDKPathsFromRuntimeLibraryImportPaths = false; + /// Don't automatically add any import paths from the SDK. + bool SkipSDKImportPaths = false; /// Scanner Prefix Mapper. std::vector ScannerPrefixMapper; @@ -619,6 +606,8 @@ class SearchPathOptions { RuntimeResourcePath, hash_combine_range(RuntimeLibraryImportPaths.begin(), RuntimeLibraryImportPaths.end()), + hash_combine_range(ImplicitFrameworkSearchPaths.begin(), + ImplicitFrameworkSearchPaths.end()), DisableModulesValidateSystemDependencies, ScannerModuleValidation, ModuleLoadMode); diff --git a/lib/AST/ASTContext.cpp b/lib/AST/ASTContext.cpp index 6c1f7693af702..36db45bf4a9de 100644 --- a/lib/AST/ASTContext.cpp +++ b/lib/AST/ASTContext.cpp @@ -2200,12 +2200,6 @@ Identifier ASTContext::getRealModuleName(Identifier key, ModuleAliasLookupOption return value.first; } -std::vector ASTContext::getDarwinImplicitFrameworkSearchPaths() -const { - assert(LangOpts.Target.isOSDarwin()); - return SearchPathOpts.getDarwinImplicitFrameworkSearchPaths(); -} - void ASTContext::loadExtensions(NominalTypeDecl *nominal, unsigned previousGeneration) { PrettyStackTraceDecl stackTrace("loading extensions for", nominal); diff --git a/lib/AST/SearchPathOptions.cpp b/lib/AST/SearchPathOptions.cpp index 23bb767a5bdf2..308c0fc4754a0 100644 --- a/lib/AST/SearchPathOptions.cpp +++ b/lib/AST/SearchPathOptions.cpp @@ -58,14 +58,10 @@ void ModuleSearchPathLookup::rebuildLookupTable(const SearchPathOptions *Opts, Entry.value().IsSystem, Entry.index()); } - // Apple platforms have extra implicit framework search paths: - // $SDKROOT/System/Library/Frameworks/ and $SDKROOT/Library/Frameworks/. - if (IsOSDarwin) { - for (auto Entry : llvm::enumerate(Opts->getDarwinImplicitFrameworkSearchPaths())) { - addFilesInPathToLookupTable(FS, Entry.value(), - ModuleSearchPathKind::DarwinImplicitFramework, - /*isSystem=*/true, Entry.index()); - } + for (auto Entry : llvm::enumerate(Opts->getImplicitFrameworkSearchPaths())) { + addFilesInPathToLookupTable(FS, Entry.value(), + ModuleSearchPathKind::ImplicitFramework, + /*isSystem=*/true, Entry.index()); } for (auto Entry : llvm::enumerate(Opts->getRuntimeLibraryImportPaths())) { @@ -123,12 +119,9 @@ void SearchPathOptions::dump(bool isDarwin) const { << Entry.value().Path << "\n"; } - if (isDarwin) { - llvm::errs() << "Darwin implicit framework search paths:\n"; - for (auto Entry : - llvm::enumerate(getDarwinImplicitFrameworkSearchPaths())) { - llvm::errs() << " [" << Entry.index() << "] " << Entry.value() << "\n"; - } + llvm::errs() << "Implicit framework search paths:\n"; + for (auto Entry : llvm::enumerate(getImplicitFrameworkSearchPaths())) { + llvm::errs() << " [" << Entry.index() << "] " << Entry.value() << "\n"; } llvm::errs() << "Runtime library import search paths:\n"; diff --git a/lib/Frontend/CompilerInvocation.cpp b/lib/Frontend/CompilerInvocation.cpp index f3f151197c8eb..fbb06f24fa3a2 100644 --- a/lib/Frontend/CompilerInvocation.cpp +++ b/lib/Frontend/CompilerInvocation.cpp @@ -254,7 +254,7 @@ static void updateRuntimeLibraryPaths(SearchPathOptions &SearchPathOpts, SearchPathOpts.RuntimeLibraryPaths.push_back(DARWIN_OS_LIBRARY_PATH); // If this is set, we don't want any runtime import paths. - if (SearchPathOpts.SkipRuntimeLibraryImportPaths) { + if (SearchPathOpts.SkipAllImplicitImportPaths) { SearchPathOpts.setRuntimeLibraryImportPaths({}); return; } @@ -270,7 +270,7 @@ static void updateRuntimeLibraryPaths(SearchPathOptions &SearchPathOpts, RuntimeLibraryImportPaths.push_back(std::string(LibPath.str())); } - if (!SearchPathOpts.ExcludeSDKPathsFromRuntimeLibraryImportPaths && !SearchPathOpts.getSDKPath().empty()) { + if (!SearchPathOpts.SkipSDKImportPaths && !SearchPathOpts.getSDKPath().empty()) { const char *swiftDir = FrontendOpts.UseSharedResourceFolder ? "swift" : "swift_static"; @@ -300,6 +300,35 @@ static void updateRuntimeLibraryPaths(SearchPathOptions &SearchPathOpts, SearchPathOpts.setRuntimeLibraryImportPaths(RuntimeLibraryImportPaths); } +static void +updateImplicitFrameworkSearchPaths(SearchPathOptions &SearchPathOpts, + const LangOptions &LangOpts) { + if (SearchPathOpts.SkipAllImplicitImportPaths) { + SearchPathOpts.setImplicitFrameworkSearchPaths({}); + return; + } + + std::vector ImplicitFrameworkSearchPaths; + if (LangOpts.Target.isOSDarwin()) { + if (!SearchPathOpts.SkipSDKImportPaths && + !SearchPathOpts.getSDKPath().empty()) { + StringRef SDKPath = SearchPathOpts.getSDKPath(); + SmallString<128> systemFrameworksScratch(SDKPath); + llvm::sys::path::append(systemFrameworksScratch, "System", "Library", + "Frameworks"); + SmallString<128> systemSubFrameworksScratch(SDKPath); + llvm::sys::path::append(systemSubFrameworksScratch, "System", "Library", + "SubFrameworks"); + SmallString<128> frameworksScratch(SDKPath); + llvm::sys::path::append(frameworksScratch, "Library", "Frameworks"); + ImplicitFrameworkSearchPaths = {systemFrameworksScratch.str().str(), + systemSubFrameworksScratch.str().str(), + frameworksScratch.str().str()}; + } + } + SearchPathOpts.setImplicitFrameworkSearchPaths(ImplicitFrameworkSearchPaths); +} + static void setIRGenOutputOptsFromFrontendOptions(IRGenOptions &IRGenOpts, const FrontendOptions &FrontendOpts) { @@ -411,11 +440,13 @@ void CompilerInvocation::setTargetTriple(StringRef Triple) { void CompilerInvocation::setTargetTriple(const llvm::Triple &Triple) { LangOpts.setTarget(Triple); updateRuntimeLibraryPaths(SearchPathOpts, FrontendOpts, LangOpts); + updateImplicitFrameworkSearchPaths(SearchPathOpts, LangOpts); } void CompilerInvocation::setSDKPath(const std::string &Path) { SearchPathOpts.setSDKPath(Path); updateRuntimeLibraryPaths(SearchPathOpts, FrontendOpts, LangOpts); + updateImplicitFrameworkSearchPaths(SearchPathOpts, LangOpts); } bool CompilerInvocation::setModuleAliasMap(std::vector args, @@ -2387,8 +2418,8 @@ static bool ParseSearchPathArgs(SearchPathOptions &Opts, ArgList &Args, if (const Arg *A = Args.getLastArg(OPT_resource_dir)) Opts.RuntimeResourcePath = A->getValue(); - Opts.SkipRuntimeLibraryImportPaths |= Args.hasArg(OPT_nostdimport); - Opts.ExcludeSDKPathsFromRuntimeLibraryImportPaths |= Args.hasArg(OPT_nostdlibimport); + Opts.SkipAllImplicitImportPaths |= Args.hasArg(OPT_nostdimport); + Opts.SkipSDKImportPaths |= Args.hasArg(OPT_nostdlibimport); Opts.DisableModulesValidateSystemDependencies |= Args.hasArg(OPT_disable_modules_validate_system_headers); @@ -4056,6 +4087,7 @@ bool CompilerInvocation::parseArgs( } updateRuntimeLibraryPaths(SearchPathOpts, FrontendOpts, LangOpts); + updateImplicitFrameworkSearchPaths(SearchPathOpts, LangOpts); setDefaultPrebuiltCacheIfNecessary(); setDefaultBlocklistsIfNecessary(); setDefaultInProcessPluginServerPathIfNecessary(); diff --git a/lib/Serialization/SerializedModuleLoader.cpp b/lib/Serialization/SerializedModuleLoader.cpp index 7973372e613bc..ab37e7c368020 100644 --- a/lib/Serialization/SerializedModuleLoader.cpp +++ b/lib/Serialization/SerializedModuleLoader.cpp @@ -108,14 +108,11 @@ std::optional forEachModuleSearchPath( callback(path.Path, ModuleSearchPathKind::Framework, path.IsSystem)) return result; - // Apple platforms have extra implicit framework search paths: - // $SDKROOT/System/Library/Frameworks/ and $SDKROOT/Library/Frameworks/. - if (Ctx.LangOpts.Target.isOSDarwin()) { - for (const auto &path : Ctx.getDarwinImplicitFrameworkSearchPaths()) - if (auto result = - callback(path, ModuleSearchPathKind::DarwinImplicitFramework, - /*isSystem=*/true)) - return result; + for (const auto &path : + Ctx.SearchPathOpts.getImplicitFrameworkSearchPaths()) { + if (auto result = callback(path, ModuleSearchPathKind::ImplicitFramework, + /*isSystem=*/true)) + return result; } for (const auto &importPath : @@ -240,7 +237,7 @@ void SerializedModuleLoaderBase::collectVisibleTopLevelModuleNamesImpl( return std::nullopt; } case ModuleSearchPathKind::Framework: - case ModuleSearchPathKind::DarwinImplicitFramework: { + case ModuleSearchPathKind::ImplicitFramework: { // Look for: // $PATH/{name}.framework/Modules/{name}.swiftmodule/{arch}.{extension} forEachDirectoryEntryPath(searchPath, [&](StringRef path) { @@ -964,7 +961,7 @@ bool SerializedModuleLoaderBase::findModule( continue; } case ModuleSearchPathKind::Framework: - case ModuleSearchPathKind::DarwinImplicitFramework: { + case ModuleSearchPathKind::ImplicitFramework: { isFramework = true; llvm::sys::path::append(currPath, moduleName + ".framework"); diff --git a/test/Frontend/default-search-paths.swift b/test/Frontend/default-search-paths.swift new file mode 100644 index 0000000000000..a6fb64c2bb450 --- /dev/null +++ b/test/Frontend/default-search-paths.swift @@ -0,0 +1,43 @@ +// UNSUPPORTED: OS=windows-msvc + +// Standard Apple paths. +// RUN: %target-swift-frontend(mock-sdk: %clang-importer-sdk-nosource) -target arm64-apple-macos15.4 -parse %s -Rmodule-loading 2>&1 | %FileCheck -check-prefix=APPLE %s +// APPLE: Implicit framework search paths: +// APPLE-NEXT: [0] SOURCE_DIR/test/Inputs/clang-importer-sdk/System/Library/Frameworks +// APPLE-NEXT: [1] SOURCE_DIR/test/Inputs/clang-importer-sdk/System/Library/SubFrameworks +// APPLE-NEXT: [2] SOURCE_DIR/test/Inputs/clang-importer-sdk/Library/Frameworks +// APPLE-NEXT: Runtime library import search paths: +// APPLE-NEXT: [0] BUILD_DIR/lib/swift/macosx +// APPLE-NEXT: [1] SOURCE_DIR/test/Inputs/clang-importer-sdk/usr/lib/swift +// APPLE-NEXT: (End of search path lists.) + +// Non-Apple platforms don't have any implicit framework search paths. +// RUN: %target-swift-frontend(mock-sdk: %clang-importer-sdk-nosource) -target x86_64-unknown-linux-android -parse %s -Rmodule-loading 2>&1 | %FileCheck -check-prefix=ANDROID %s +// ANDROID: Implicit framework search paths: +// ANDROID-NEXT: Runtime library import search paths: +// ANDROID-NEXT: [0] BUILD_DIR/lib/swift/android +// ANDROID-NEXT: [1] BUILD_DIR/lib/swift/android/x86_64 +// ANDROID-NEXT: [2] SOURCE_DIR/test/Inputs/clang-importer-sdk/usr/lib/swift/android +// ANDROID-NEXT: [3] SOURCE_DIR/test/Inputs/clang-importer-sdk/usr/lib/swift/android/x86_64 +// ANDROID-NEXT: (End of search path lists.) + +// -nostdimport doesn't set up any standard import paths at all. +// RUN: %target-swift-frontend(mock-sdk: %clang-importer-sdk-nosource) -target arm64-apple-macos15.4 -nostdimport -parse %s -Rmodule-loading 2>&1 | %FileCheck -check-prefix=NOSTDIMPORT %s +// RUN: %target-swift-frontend(mock-sdk: %clang-importer-sdk-nosource) -target x86_64-unknown-linux-android -nostdimport -parse %s -Rmodule-loading 2>&1 | %FileCheck -check-prefix=NOSTDIMPORT %s +// NOSTDIMPORT: Implicit framework search paths: +// NOSTDIMPORT-NEXT: Runtime library import search paths: +// NOSTDIMPORT-NEXT: (End of search path lists.) + +// -nostdlibimport removes all of the standard imports from the SDK but leaves the toolchain ones. +// RUN: %target-swift-frontend(mock-sdk: %clang-importer-sdk-nosource) -target arm64-apple-macos15.4 -nostdlibimport -parse %s -Rmodule-loading 2>&1 | %FileCheck -check-prefix=APPLE-NOSTDLIBIMPORT %s +// APPLE-NOSTDLIBIMPORT: Implicit framework search paths: +// APPLE-NOSTDLIBIMPORT-NEXT: Runtime library import search paths: +// APPLE-NOSTDLIBIMPORT-NEXT: [0] BUILD_DIR/lib/swift/macosx +// APPLE-NOSTDLIBIMPORT-NEXT: (End of search path lists.) + +// RUN: %target-swift-frontend(mock-sdk: %clang-importer-sdk-nosource) -target x86_64-unknown-linux-android -nostdlibimport -parse %s -Rmodule-loading 2>&1 | %FileCheck -check-prefix=ANDROID-NOSTDLIBIMPORT %s +// ANDROID-NOSTDLIBIMPORT: Implicit framework search paths: +// ANDROID-NOSTDLIBIMPORT-NEXT: Runtime library import search paths: +// ANDROID-NOSTDLIBIMPORT-NEXT: [0] BUILD_DIR/lib/swift/android +// ANDROID-NOSTDLIBIMPORT-NEXT: [1] BUILD_DIR/lib/swift/android/x86_64 +// ANDROID-NOSTDLIBIMPORT-NEXT: (End of search path lists.)