Skip to content

Commit f82150b

Browse files
authored
Merge pull request #33678 from drexin/wip-backport-static-linking-5.3
[5.3] Properly compute resource folder when linking statically
2 parents f9c6f3a + e8fe229 commit f82150b

File tree

14 files changed

+239
-29
lines changed

14 files changed

+239
-29
lines changed

include/swift/Frontend/Frontend.h

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -128,7 +128,8 @@ class CompilerInvocation {
128128
bool parseArgs(ArrayRef<const char *> Args, DiagnosticEngine &Diags,
129129
SmallVectorImpl<std::unique_ptr<llvm::MemoryBuffer>>
130130
*ConfigurationFileBuffers = nullptr,
131-
StringRef workingDirectory = {});
131+
StringRef workingDirectory = {},
132+
StringRef mainExecutablePath = {});
132133

133134
/// Sets specific options based on the given serialized Swift binary data.
134135
///
@@ -213,8 +214,11 @@ class CompilerInvocation {
213214
/// Computes the runtime resource path relative to the given Swift
214215
/// executable.
215216
static void computeRuntimeResourcePathFromExecutablePath(
216-
StringRef mainExecutablePath,
217-
llvm::SmallString<128> &runtimeResourcePath);
217+
StringRef mainExecutablePath, bool shared,
218+
llvm::SmallVectorImpl<char> &runtimeResourcePath);
219+
220+
/// Appends `lib/swift[_static]` to the given path
221+
static void appendSwiftLibDir(llvm::SmallVectorImpl<char> &path, bool shared);
218222

219223
void setSDKPath(const std::string &Path);
220224

include/swift/Frontend/FrontendOptions.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -301,6 +301,11 @@ class FrontendOptions {
301301
/// Indicates whether the action will immediately run code.
302302
static bool isActionImmediate(ActionType);
303303

304+
/// Determines whether the static or shared resource folder is used.
305+
/// When set to `true`, the default resource folder will be set to
306+
/// '.../lib/swift', otherwise '.../lib/swift_static'.
307+
bool UseSharedResourceFolder = true;
308+
304309
/// \return true if action only parses without doing other compilation steps.
305310
static bool shouldActionOnlyParse(ActionType);
306311

include/swift/Option/FrontendOptions.td

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -719,4 +719,8 @@ def target_sdk_version : Separate<["-"], "target-sdk-version">,
719719
def target_variant_sdk_version : Separate<["-"], "target-variant-sdk-version">,
720720
HelpText<"The version of target variant SDK used for compilation">;
721721

722+
723+
def use_static_resource_dir
724+
: Flag<["-"], "use-static-resource-dir">,
725+
HelpText<"Use resources in the static resource directory">;
722726
} // end let Flags = [FrontendOption, NoDriverOption, HelpHidden]

lib/Driver/Driver.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2248,6 +2248,13 @@ bool Driver::handleImmediateArgs(const ArgList &Args, const ToolChain &TC) {
22482248
commandLine.push_back(resourceDirArg->getValue());
22492249
}
22502250

2251+
if (Args.hasFlag(options::OPT_static_executable,
2252+
options::OPT_no_static_executable, false) ||
2253+
Args.hasFlag(options::OPT_static_stdlib, options::OPT_no_static_stdlib,
2254+
false)) {
2255+
commandLine.push_back("-use-static-resource-dir");
2256+
}
2257+
22512258
std::string executable = getSwiftProgramPath();
22522259

22532260
// FIXME: This bypasses mechanisms like -v and -###. (SR-12119)

lib/Driver/ToolChains.cpp

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222
#include "swift/Driver/Compilation.h"
2323
#include "swift/Driver/Driver.h"
2424
#include "swift/Driver/Job.h"
25+
#include "swift/Frontend/Frontend.h"
2526
#include "swift/Option/Options.h"
2627
#include "clang/Basic/Version.h"
2728
#include "clang/Driver/Util.h"
@@ -523,6 +524,13 @@ ToolChain::constructInvocation(const CompileJobAction &job,
523524
Arguments.push_back("-track-system-dependencies");
524525
}
525526

527+
if (context.Args.hasFlag(options::OPT_static_executable,
528+
options::OPT_no_static_executable, false) ||
529+
context.Args.hasFlag(options::OPT_static_stdlib,
530+
options::OPT_no_static_stdlib, false)) {
531+
Arguments.push_back("-use-static-resource-dir");
532+
}
533+
526534
context.Args.AddLastArg(
527535
Arguments,
528536
options::
@@ -1256,24 +1264,18 @@ void ToolChain::getClangLibraryPath(const ArgList &Args,
12561264
void ToolChain::getResourceDirPath(SmallVectorImpl<char> &resourceDirPath,
12571265
const llvm::opt::ArgList &args,
12581266
bool shared) const {
1259-
// FIXME: Duplicated from CompilerInvocation, but in theory the runtime
1260-
// library link path and the standard library module import path don't
1261-
// need to be the same.
12621267
if (const Arg *A = args.getLastArg(options::OPT_resource_dir)) {
12631268
StringRef value = A->getValue();
12641269
resourceDirPath.append(value.begin(), value.end());
12651270
} else if (!getTriple().isOSDarwin() && args.hasArg(options::OPT_sdk)) {
12661271
StringRef value = args.getLastArg(options::OPT_sdk)->getValue();
12671272
resourceDirPath.append(value.begin(), value.end());
1268-
llvm::sys::path::append(resourceDirPath, "usr", "lib",
1269-
shared ? "swift" : "swift_static");
1273+
llvm::sys::path::append(resourceDirPath, "usr");
1274+
CompilerInvocation::appendSwiftLibDir(resourceDirPath, shared);
12701275
} else {
12711276
auto programPath = getDriver().getSwiftProgramPath();
1272-
resourceDirPath.append(programPath.begin(), programPath.end());
1273-
llvm::sys::path::remove_filename(resourceDirPath); // remove /swift
1274-
llvm::sys::path::remove_filename(resourceDirPath); // remove /bin
1275-
llvm::sys::path::append(resourceDirPath, "lib",
1276-
shared ? "swift" : "swift_static");
1277+
CompilerInvocation::computeRuntimeResourcePathFromExecutablePath(
1278+
programPath, shared, resourceDirPath);
12771279
}
12781280

12791281
StringRef libSubDir = getPlatformNameForTriple(getTriple());

lib/Frontend/ArgsToFrontendOptionsConverter.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,7 @@ bool ArgsToFrontendOptionsConverter::convert(
187187
Opts.EnableSourceImport |= Args.hasArg(OPT_enable_source_import);
188188
Opts.ImportUnderlyingModule |= Args.hasArg(OPT_import_underlying_module);
189189
Opts.EnableIncrementalDependencyVerifier |= Args.hasArg(OPT_verify_incremental_dependencies);
190+
Opts.UseSharedResourceFolder = !Args.hasArg(OPT_use_static_resource_dir);
190191

191192
computeImportObjCHeaderOptions();
192193
computeImplicitImportModuleNames();

lib/Frontend/CompilerInvocation.cpp

Lines changed: 19 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -39,16 +39,25 @@ swift::CompilerInvocation::CompilerInvocation() {
3939
}
4040

4141
void CompilerInvocation::computeRuntimeResourcePathFromExecutablePath(
42-
StringRef mainExecutablePath, llvm::SmallString<128> &runtimeResourcePath) {
43-
runtimeResourcePath.assign(mainExecutablePath);
42+
StringRef mainExecutablePath, bool shared,
43+
llvm::SmallVectorImpl<char> &runtimeResourcePath) {
44+
runtimeResourcePath.append(mainExecutablePath.begin(),
45+
mainExecutablePath.end());
46+
4447
llvm::sys::path::remove_filename(runtimeResourcePath); // Remove /swift
4548
llvm::sys::path::remove_filename(runtimeResourcePath); // Remove /bin
46-
llvm::sys::path::append(runtimeResourcePath, "lib", "swift");
49+
appendSwiftLibDir(runtimeResourcePath, shared);
50+
}
51+
52+
void CompilerInvocation::appendSwiftLibDir(llvm::SmallVectorImpl<char> &path,
53+
bool shared) {
54+
llvm::sys::path::append(path, "lib", shared ? "swift" : "swift_static");
4755
}
4856

4957
void CompilerInvocation::setMainExecutablePath(StringRef Path) {
5058
llvm::SmallString<128> LibPath;
51-
computeRuntimeResourcePathFromExecutablePath(Path, LibPath);
59+
computeRuntimeResourcePathFromExecutablePath(
60+
Path, FrontendOpts.UseSharedResourceFolder, LibPath);
5261
setRuntimeResourcePath(LibPath.str());
5362

5463
llvm::SmallString<128> DiagnosticDocsPath(Path);
@@ -1597,11 +1606,10 @@ static bool ParseMigratorArgs(MigratorOptions &Opts,
15971606
}
15981607

15991608
bool CompilerInvocation::parseArgs(
1600-
ArrayRef<const char *> Args,
1601-
DiagnosticEngine &Diags,
1609+
ArrayRef<const char *> Args, DiagnosticEngine &Diags,
16021610
SmallVectorImpl<std::unique_ptr<llvm::MemoryBuffer>>
16031611
*ConfigurationFileBuffers,
1604-
StringRef workingDirectory) {
1612+
StringRef workingDirectory, StringRef mainExecutablePath) {
16051613
using namespace options;
16061614

16071615
if (Args.empty())
@@ -1632,6 +1640,10 @@ bool CompilerInvocation::parseArgs(
16321640
return true;
16331641
}
16341642

1643+
if (!mainExecutablePath.empty()) {
1644+
setMainExecutablePath(mainExecutablePath);
1645+
}
1646+
16351647
ParseModuleInterfaceArgs(ModuleInterfaceOpts, ParsedArgs);
16361648
SaveModuleInterfaceArgs(ModuleInterfaceOpts, FrontendOpts, ParsedArgs, Diags);
16371649

lib/FrontendTool/FrontendTool.cpp

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2078,17 +2078,18 @@ int swift::performFrontend(ArrayRef<const char *> Args,
20782078
}
20792079

20802080
CompilerInvocation Invocation;
2081-
std::string MainExecutablePath = llvm::sys::fs::getMainExecutable(Argv0,
2082-
MainAddr);
2083-
Invocation.setMainExecutablePath(MainExecutablePath);
20842081

20852082
SmallString<128> workingDirectory;
20862083
llvm::sys::fs::current_path(workingDirectory);
20872084

2085+
std::string MainExecutablePath =
2086+
llvm::sys::fs::getMainExecutable(Argv0, MainAddr);
2087+
20882088
// Parse arguments.
20892089
SmallVector<std::unique_ptr<llvm::MemoryBuffer>, 4> configurationFileBuffers;
20902090
if (Invocation.parseArgs(Args, Instance->getDiags(),
2091-
&configurationFileBuffers, workingDirectory)) {
2091+
&configurationFileBuffers, workingDirectory,
2092+
MainExecutablePath)) {
20922093
return finishDiagProcessing(1, /*verifierEnabled*/ false);
20932094
}
20942095

stdlib/cmake/modules/AddSwiftStdlib.cmake

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -628,6 +628,9 @@ function(_add_swift_target_library_single target name)
628628
"${SWIFTLIB_SINGLE_multiple_parameter_options}"
629629
${ARGN})
630630

631+
translate_flag(${SWIFTLIB_SINGLE_STATIC} "STATIC"
632+
SWIFTLIB_SINGLE_STATIC_keyword)
633+
631634
# Determine macCatalyst build flavor
632635
get_maccatalyst_build_flavor(maccatalyst_build_flavor
633636
"${SWIFTLIB_SINGLE_SDK}" "${SWIFTLIB_SINGLE_MACCATALYST_BUILD_FLAVOR}")
@@ -757,6 +760,7 @@ function(_add_swift_target_library_single target name)
757760
${SWIFTLIB_SINGLE_IS_STDLIB_CORE_keyword}
758761
${SWIFTLIB_SINGLE_IS_SDK_OVERLAY_keyword}
759762
${embed_bitcode_arg}
763+
${SWIFTLIB_SINGLE_STATIC_keyword}
760764
INSTALL_IN_COMPONENT "${SWIFTLIB_SINGLE_INSTALL_IN_COMPONENT}"
761765
MACCATALYST_BUILD_FLAVOR "${SWIFTLIB_SINGLE_MACCATALYST_BUILD_FLAVOR}")
762766
add_swift_source_group("${SWIFTLIB_SINGLE_EXTERNAL_SOURCES}")

stdlib/cmake/modules/SwiftSource.cmake

Lines changed: 67 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ function(handle_swift_sources
2929
dependency_sibgen_target_out_var_name
3030
sourcesvar externalvar name)
3131
cmake_parse_arguments(SWIFTSOURCES
32-
"IS_MAIN;IS_STDLIB;IS_STDLIB_CORE;IS_SDK_OVERLAY;EMBED_BITCODE"
32+
"IS_MAIN;IS_STDLIB;IS_STDLIB_CORE;IS_SDK_OVERLAY;EMBED_BITCODE;STATIC"
3333
"SDK;ARCHITECTURE;INSTALL_IN_COMPONENT;MACCATALYST_BUILD_FLAVOR"
3434
"DEPENDS;COMPILE_FLAGS;MODULE_NAME"
3535
${ARGN})
@@ -41,6 +41,8 @@ function(handle_swift_sources
4141
IS_SDK_OVERLAY_arg)
4242
translate_flag(${SWIFTSOURCES_EMBED_BITCODE} "EMBED_BITCODE"
4343
EMBED_BITCODE_arg)
44+
translate_flag(${SWIFTSOURCES_STATIC} "STATIC"
45+
STATIC_arg)
4446

4547
if(SWIFTSOURCES_IS_MAIN)
4648
set(SWIFTSOURCES_INSTALL_IN_COMPONENT never_install)
@@ -278,13 +280,15 @@ endfunction()
278280
# [MODULE_NAME] # The module name.
279281
# [INSTALL_IN_COMPONENT] # Install produced files.
280282
# [EMBED_BITCODE] # Embed LLVM bitcode into the .o files
283+
# [STATIC] # Also write .swiftmodule etc. to static
284+
# # resource folder
281285
# )
282286
function(_compile_swift_files
283287
dependency_target_out_var_name dependency_module_target_out_var_name
284288
dependency_sib_target_out_var_name dependency_sibopt_target_out_var_name
285289
dependency_sibgen_target_out_var_name)
286290
cmake_parse_arguments(SWIFTFILE
287-
"IS_MAIN;IS_STDLIB;IS_STDLIB_CORE;IS_SDK_OVERLAY;EMBED_BITCODE"
291+
"IS_MAIN;IS_STDLIB;IS_STDLIB_CORE;IS_SDK_OVERLAY;EMBED_BITCODE;STATIC"
288292
"OUTPUT;MODULE_NAME;INSTALL_IN_COMPONENT;MACCATALYST_BUILD_FLAVOR"
289293
"SOURCES;FLAGS;DEPENDS;SDK;ARCHITECTURE;OPT_FLAGS;MODULE_DIR"
290294
${ARGN})
@@ -448,8 +452,11 @@ function(_compile_swift_files
448452
endforeach()
449453

450454
set(module_file)
455+
set(module_file_static)
451456
set(module_doc_file)
457+
set(module_doc_file_static)
452458
set(interface_file)
459+
set(interface_file_static)
453460

454461
if(NOT SWIFTFILE_IS_MAIN)
455462
# Determine the directory where the module file should be placed.
@@ -464,17 +471,28 @@ function(_compile_swift_files
464471
list(APPEND swift_flags "-parse-as-library")
465472

466473
set(module_base "${module_dir}/${SWIFTFILE_MODULE_NAME}")
474+
475+
set(module_dir_static "${SWIFTSTATICLIB_DIR}/${library_subdir}")
476+
set(module_base_static "${module_dir_static}/${SWIFTFILE_MODULE_NAME}")
477+
467478
set(module_triple ${SWIFT_SDK_${library_subdir_sdk}_ARCH_${SWIFTFILE_ARCHITECTURE}_MODULE})
468479
if(SWIFTFILE_SDK IN_LIST SWIFT_APPLE_PLATFORMS OR
469480
SWIFTFILE_SDK STREQUAL "MACCATALYST")
470481
set(specific_module_dir "${module_base}.swiftmodule")
471482
set(module_base "${module_base}.swiftmodule/${module_triple}")
483+
484+
set(specific_module_dir_static "${module_base_static}.swiftmodule")
485+
set(module_base_static "${module_base_static}.swiftmodule/${module_triple}")
472486
else()
473487
set(specific_module_dir)
488+
set(specific_module_dir_static)
474489
endif()
475490
set(module_file "${module_base}.swiftmodule")
476491
set(module_doc_file "${module_base}.swiftdoc")
477492

493+
set(module_file_static "${module_base_static}.swiftmodule")
494+
set(module_doc_file_static "${module_base_static}.swiftdoc")
495+
478496
# FIXME: These don't really belong inside the swiftmodule, but there's not
479497
# an obvious alternate place to put them.
480498
set(sib_file "${module_base}.Onone.sib")
@@ -483,6 +501,7 @@ function(_compile_swift_files
483501

484502
if(SWIFT_ENABLE_MODULE_INTERFACES)
485503
set(interface_file "${module_base}.swiftinterface")
504+
set(interface_file_static "${module_base_static}.swiftinterface")
486505
list(APPEND swift_module_flags
487506
"-emit-module-interface-path" "${interface_file}")
488507
endif()
@@ -510,10 +529,20 @@ function(_compile_swift_files
510529
swift_install_in_component(DIRECTORY "${specific_module_dir}"
511530
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/${library_subdir}"
512531
COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}")
532+
if(SWIFTFILE_STATIC)
533+
swift_install_in_component(DIRECTORY "${specific_module_dir_static}"
534+
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift_static/${library_subdir}"
535+
COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}")
536+
endif()
513537
else()
514538
swift_install_in_component(FILES ${module_outputs}
515539
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/${library_subdir}"
516540
COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}")
541+
if(SWIFTFILE_STATIC)
542+
swift_install_in_component(FILES ${module_outputs}
543+
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift_static/${library_subdir}"
544+
COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}")
545+
endif()
517546
endif()
518547

519548
# macCatalyst zippered module setup
@@ -563,8 +592,10 @@ function(_compile_swift_files
563592
endif()
564593

565594
set(module_outputs "${module_file}" "${module_doc_file}")
595+
set(module_outputs_static "${module_file_static}" "${module_doc_file_static}")
566596
if(interface_file)
567597
list(APPEND module_outputs "${interface_file}")
598+
list(APPEND module_outputs_static "${interface_file_static}")
568599
endif()
569600

570601
if(SWIFTFILE_SDK IN_LIST SWIFT_APPLE_PLATFORMS)
@@ -573,10 +604,23 @@ function(_compile_swift_files
573604
COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}"
574605
OPTIONAL
575606
PATTERN "Project" EXCLUDE)
607+
608+
if(SWIFTFILE_STATIC)
609+
swift_install_in_component(DIRECTORY "${specific_module_dir_static}"
610+
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift_static/${library_subdir}"
611+
COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}"
612+
OPTIONAL
613+
PATTERN "Project" EXCLUDE)
614+
endif()
576615
else()
577616
swift_install_in_component(FILES ${module_outputs}
578617
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/${library_subdir}"
579618
COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}")
619+
if(SWIFTFILE_STATIC)
620+
swift_install_in_component(FILES ${module_outputs}
621+
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift_static/${library_subdir}"
622+
COMPONENT "${SWIFTFILE_INSTALL_IN_COMPONENT}")
623+
endif()
580624
endif()
581625

582626
set(line_directive_tool "${SWIFT_SOURCE_DIR}/utils/line-directive")
@@ -758,7 +802,27 @@ function(_compile_swift_files
758802
${swift_ide_test_dependency}
759803
${create_dirs_dependency_target}
760804
COMMENT "Generating ${module_file}")
761-
set("${dependency_module_target_out_var_name}" "${module_dependency_target}" PARENT_SCOPE)
805+
806+
if(SWIFTFILE_STATIC)
807+
add_custom_command_target(
808+
module_dependency_target_static
809+
COMMAND
810+
"${CMAKE_COMMAND}" "-E" "make_directory" ${module_dir_static}
811+
${specific_module_dir_static}
812+
COMMAND
813+
"${CMAKE_COMMAND}" "-E" "copy" ${module_file} ${module_file_static}
814+
COMMAND
815+
"${CMAKE_COMMAND}" "-E" "copy" ${module_doc_file} ${module_doc_file_static}
816+
COMMAND
817+
"${CMAKE_COMMAND}" "-E" "copy" ${interface_file} ${interface_file_static}
818+
OUTPUT ${module_outputs_static}
819+
DEPENDS
820+
"${module_dependency_target}"
821+
COMMENT "Generating ${module_file}")
822+
set("${dependency_module_target_out_var_name}" "${module_dependency_target_static}" PARENT_SCOPE)
823+
else()
824+
set("${dependency_module_target_out_var_name}" "${module_dependency_target}" PARENT_SCOPE)
825+
endif()
762826

763827
# macCatalyst zippered swiftmodule
764828
if(maccatalyst_build_flavor STREQUAL "zippered")

0 commit comments

Comments
 (0)