Skip to content

Commit 0c42b57

Browse files
committed
ELF: restructure image metadata registration
Restructure the ELF handling to be completely agnostic to the OS. Rather than usng the loader to query the section information, use the linker to construct linker tables and synthetic markers for the beginning and of the table. Save off the values of these pointers and pass them along through the constructor to the runtime for registration. This removes the need for the begin/end objects. Remove the special construction of the begin/end objects through the special assembly constructs, preferring to do this in C with a bit of inline assembly to ensure that the section is always allocated. Remove the special handling for the various targets, the empty object file can be linked on all the targets. The new object file has no requirements on the ordering. It needs to simply be injected into the link. Name the replacement file `swiftrt.o` mirroring `crt.o` from libc. Merge the constructor and the definition into a single object file. This approach is generally more portable, overall simpler to implement, and more robust. Thanks to Orlando Bassotto for help analyzing some of the odd behaviours when switching over.
1 parent f5989d2 commit 0c42b57

20 files changed

+222
-760
lines changed

cmake/modules/AddSwift.cmake

Lines changed: 9 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -716,19 +716,6 @@ function(_add_swift_library_single target name)
716716
set(SWIFTLIB_SINGLE_API_NOTES "${module_name}")
717717
endif()
718718

719-
# On platforms that use ELF binaries we add markers for metadata sections in
720-
# the shared libraries using these object files. This wouldn't be necessary
721-
# if the link was done by the swift binary: rdar://problem/19007002
722-
if(SWIFTLIB_SINGLE_TARGET_LIBRARY AND
723-
"${SWIFT_SDK_${SWIFTLIB_SINGLE_SDK}_OBJECT_FORMAT}" STREQUAL "ELF")
724-
if("${libkind}" STREQUAL "SHARED")
725-
set(arch_subdir "${SWIFTLIB_DIR}/${SWIFTLIB_SINGLE_SUBDIR}")
726-
727-
set(SWIFT_SECTIONS_OBJECT_BEGIN "${arch_subdir}/swift_begin.o")
728-
set(SWIFT_SECTIONS_OBJECT_END "${arch_subdir}/swift_end.o")
729-
endif()
730-
endif()
731-
732719
if("${SWIFTLIB_SINGLE_SDK}" STREQUAL "WINDOWS")
733720
swift_windows_include_for_arch(${SWIFTLIB_SINGLE_ARCHITECTURE} SWIFTLIB_INCLUDE)
734721
swift_windows_generate_sdk_vfs_overlay(SWIFTLIB_SINGLE_VFS_OVERLAY_FLAGS)
@@ -828,12 +815,15 @@ function(_add_swift_library_single target name)
828815
endif()
829816

830817
add_library("${target}" ${libkind}
831-
${SWIFT_SECTIONS_OBJECT_BEGIN}
832-
${SWIFTLIB_SINGLE_SOURCES}
833-
${SWIFTLIB_SINGLE_EXTERNAL_SOURCES}
834-
${INCORPORATED_OBJECT_LIBRARIES_EXPRESSIONS}
835-
${SWIFTLIB_SINGLE_XCODE_WORKAROUND_SOURCES}
836-
${SWIFT_SECTIONS_OBJECT_END})
818+
${SWIFTLIB_SINGLE_SOURCES}
819+
${SWIFTLIB_SINGLE_EXTERNAL_SOURCES}
820+
${INCORPORATED_OBJECT_LIBRARIES_EXPRESSIONS}
821+
${SWIFTLIB_SINGLE_XCODE_WORKAROUND_SOURCES})
822+
if("${SWIFT_SDK_${SWIFTLIB_SINGLE_SDK}_OBJECT_FORMAT}" STREQUAL "ELF" AND SWIFTLIB_TARGET_LIBRARY)
823+
if("${libkind}" STREQUAL "SHARED")
824+
target_sources(${target} PRIVATE $<TARGET_OBJECTS:swiftImageRegistrationObject-${SWIFT_SDK_${sdk}_LIB_SUBDIR}-${SWIFTLIB_SINGLE_ARCHITECTURE}>)
825+
endif()
826+
endif()
837827
_set_target_prefix_and_suffix("${target}" "${libkind}" "${SWIFTLIB_SINGLE_SDK}")
838828

839829
if(SWIFTLIB_SINGLE_TARGET_LIBRARY)
@@ -872,17 +862,6 @@ function(_add_swift_library_single target name)
872862
set_property(TARGET "${target}" PROPERTY NO_SONAME ON)
873863
endif()
874864

875-
# The section metadata objects are generated sources, and we need to tell CMake
876-
# not to expect to find them prior to their generation.
877-
if(SWIFTLIB_SINGLE_TARGET_LIBRARY AND
878-
"${SWIFT_SDK_${SWIFTLIB_SINGLE_SDK}_OBJECT_FORMAT}" STREQUAL "ELF")
879-
if("${libkind}" STREQUAL "SHARED")
880-
set_source_files_properties(${SWIFT_SECTIONS_OBJECT_BEGIN} PROPERTIES GENERATED 1)
881-
set_source_files_properties(${SWIFT_SECTIONS_OBJECT_END} PROPERTIES GENERATED 1)
882-
add_dependencies("${target}" section_magic)
883-
endif()
884-
endif()
885-
886865
llvm_update_compile_flags(${target})
887866

888867
set_output_directory(${target}

lib/Driver/ToolChains.cpp

Lines changed: 8 additions & 56 deletions
Original file line numberDiff line numberDiff line change
@@ -1530,26 +1530,6 @@ bool toolchains::GenericUnix::shouldProvideRPathToLinker() const {
15301530
return true;
15311531
}
15321532

1533-
std::string toolchains::GenericUnix::getPreInputObjectPath(
1534-
StringRef RuntimeLibraryPath) const {
1535-
// On Linux and FreeBSD and Haiku (really, ELF binaries) we need to add objects
1536-
// to provide markers and size for the metadata sections.
1537-
SmallString<128> PreInputObjectPath = RuntimeLibraryPath;
1538-
llvm::sys::path::append(PreInputObjectPath,
1539-
swift::getMajorArchitectureName(getTriple()));
1540-
llvm::sys::path::append(PreInputObjectPath, "swift_begin.o");
1541-
return PreInputObjectPath.str();
1542-
}
1543-
1544-
std::string toolchains::GenericUnix::getPostInputObjectPath(
1545-
StringRef RuntimeLibraryPath) const {
1546-
SmallString<128> PostInputObjectPath = RuntimeLibraryPath;
1547-
llvm::sys::path::append(PostInputObjectPath,
1548-
swift::getMajorArchitectureName(getTriple()));
1549-
llvm::sys::path::append(PostInputObjectPath, "swift_end.o");
1550-
return PostInputObjectPath.str();
1551-
}
1552-
15531533
ToolChain::InvocationInfo
15541534
toolchains::GenericUnix::constructInvocation(const LinkJobAction &job,
15551535
const JobContext &context) const {
@@ -1627,22 +1607,10 @@ toolchains::GenericUnix::constructInvocation(const LinkJobAction &job,
16271607
}
16281608

16291609
SmallString<128> SharedRuntimeLibPath;
1630-
SmallString<128> StaticRuntimeLibPath;
1631-
// Path to swift_begin.o and swift_end.o.
1632-
SmallString<128> ObjectLibPath;
16331610
getRuntimeLibraryPath(SharedRuntimeLibPath, context.Args, *this);
16341611

1635-
// -static-stdlib uses the static lib path for libswiftCore but
1636-
// the shared lib path for swift_begin.o and swift_end.o.
1637-
if (staticExecutable || staticStdlib) {
1638-
getRuntimeStaticLibraryPath(StaticRuntimeLibPath, context.Args, *this);
1639-
}
1640-
1641-
if (staticExecutable) {
1642-
ObjectLibPath = StaticRuntimeLibPath;
1643-
} else {
1644-
ObjectLibPath = SharedRuntimeLibPath;
1645-
}
1612+
SmallString<128> StaticRuntimeLibPath;
1613+
getRuntimeStaticLibraryPath(StaticRuntimeLibPath, context.Args, *this);
16461614

16471615
// Add the runtime library link path, which is platform-specific and found
16481616
// relative to the compiler.
@@ -1655,10 +1623,12 @@ toolchains::GenericUnix::constructInvocation(const LinkJobAction &job,
16551623
Arguments.push_back(context.Args.MakeArgString(SharedRuntimeLibPath));
16561624
}
16571625

1658-
auto PreInputObjectPath = getPreInputObjectPath(ObjectLibPath);
1659-
if (!PreInputObjectPath.empty()) {
1660-
Arguments.push_back(context.Args.MakeArgString(PreInputObjectPath));
1661-
}
1626+
SmallString<128> swiftrtPath = SharedRuntimeLibPath;
1627+
llvm::sys::path::append(swiftrtPath,
1628+
swift::getMajorArchitectureName(getTriple()));
1629+
llvm::sys::path::append(swiftrtPath, "swiftrt.o");
1630+
Arguments.push_back(context.Args.MakeArgString(swiftrtPath));
1631+
16621632
addPrimaryInputsOfType(Arguments, context.Inputs, types::TY_Object);
16631633
addInputsOfType(Arguments, context.InputActions, types::TY_Object);
16641634

@@ -1753,13 +1723,6 @@ toolchains::GenericUnix::constructInvocation(const LinkJobAction &job,
17531723
context.Args.AddAllArgs(Arguments, options::OPT_Xlinker);
17541724
context.Args.AddAllArgs(Arguments, options::OPT_linker_option_Group);
17551725

1756-
// Just before the output option, allow GenericUnix toolchains to add
1757-
// additional inputs.
1758-
auto PostInputObjectPath = getPostInputObjectPath(ObjectLibPath);
1759-
if (!PostInputObjectPath.empty()) {
1760-
Arguments.push_back(context.Args.MakeArgString(PostInputObjectPath));
1761-
}
1762-
17631726
// This should be the last option, for convenience in checking output.
17641727
Arguments.push_back("-o");
17651728
Arguments.push_back(context.Output.getPrimaryOutputFilename().c_str());
@@ -1792,14 +1755,3 @@ std::string toolchains::Cygwin::getTargetForLinker() const {
17921755
return "";
17931756
}
17941757

1795-
std::string toolchains::Cygwin::getPreInputObjectPath(
1796-
StringRef RuntimeLibraryPath) const {
1797-
// Cygwin does not add "begin" and "end" objects.
1798-
return "";
1799-
}
1800-
1801-
std::string toolchains::Cygwin::getPostInputObjectPath(
1802-
StringRef RuntimeLibraryPath) const {
1803-
// Cygwin does not add "begin" and "end" objects.
1804-
return "";
1805-
}

lib/Driver/ToolChains.h

Lines changed: 0 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -66,30 +66,6 @@ class LLVM_LIBRARY_VISIBILITY GenericUnix : public ToolChain {
6666
/// default is to return true (and so specify an -rpath).
6767
virtual bool shouldProvideRPathToLinker() const;
6868

69-
/// Provides a path to an object that should be linked first. On platforms
70-
/// that use ELF binaries, an object that provides markers and sizes for
71-
/// metadata sections must be linked first. Platforms that do not need this
72-
/// object may return an empty string; no additional objects are linked in
73-
/// this case.
74-
///
75-
/// \param RuntimeLibraryPath A path to the Swift resource directory, which
76-
/// on ARM architectures will contain metadata "begin" and "end"
77-
/// objects.
78-
virtual std::string
79-
getPreInputObjectPath(StringRef RuntimeLibraryPath) const;
80-
81-
/// Provides a path to an object that should be linked last. On platforms
82-
/// that use ELF binaries, an object that provides markers and sizes for
83-
/// metadata sections must be linked last. Platforms that do not need this
84-
/// object may return an empty string; no additional objects are linked in
85-
/// this case.
86-
///
87-
/// \param RuntimeLibraryPath A path to the Swift resource directory, which
88-
/// on ARM architectures will contain metadata "begin" and "end"
89-
/// objects.
90-
virtual std::string
91-
getPostInputObjectPath(StringRef RuntimeLibraryPath) const;
92-
9369
InvocationInfo constructInvocation(const LinkJobAction &job,
9470
const JobContext &context) const override;
9571

@@ -117,11 +93,6 @@ class LLVM_LIBRARY_VISIBILITY Cygwin : public GenericUnix {
11793

11894
std::string getTargetForLinker() const override;
11995

120-
std::string getPreInputObjectPath(
121-
StringRef RuntimeLibraryPath) const override;
122-
123-
std::string getPostInputObjectPath(
124-
StringRef RuntimeLibraryPath) const override;
12596
public:
12697
Cygwin(const Driver &D, const llvm::Triple &Triple) : GenericUnix(D, Triple) {}
12798
~Cygwin() = default;

lib/IRGen/GenDecl.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2329,7 +2329,7 @@ llvm::Constant *IRGenModule::emitProtocolConformances() {
23292329
sectionName = "__TEXT, __swift2_proto, regular, no_dead_strip";
23302330
break;
23312331
case llvm::Triple::ELF:
2332-
sectionName = ".swift2_protocol_conformances";
2332+
sectionName = "swift2_protocol_conformances";
23332333
break;
23342334
case llvm::Triple::COFF:
23352335
sectionName = ".sw2prtc";
@@ -2352,7 +2352,7 @@ llvm::Constant *IRGenModule::emitTypeMetadataRecords() {
23522352
sectionName = "__TEXT, __swift2_types, regular, no_dead_strip";
23532353
break;
23542354
case llvm::Triple::ELF:
2355-
sectionName = ".swift2_type_metadata";
2355+
sectionName = "swift2_type_metadata";
23562356
break;
23572357
case llvm::Triple::COFF:
23582358
sectionName = ".sw2tymd";

lib/IRGen/GenReflection.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -769,7 +769,7 @@ static std::string getReflectionSectionName(IRGenModule &IGM,
769769
OS << ".sw3" << FourCC;
770770
break;
771771
case llvm::Triple::ELF:
772-
OS << ".swift3_" << LongName;
772+
OS << "swift3_" << LongName;
773773
break;
774774
case llvm::Triple::MachO:
775775
assert(LongName.size() <= 7 &&

stdlib/public/core/CMakeLists.txt

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -249,7 +249,6 @@ add_swift_library(swiftCore ${SWIFT_STDLIB_LIBRARY_BUILD_TYPES} IS_STDLIB IS_STD
249249
# and the generated directory as dependencies.
250250
FILE_DEPENDS
251251
copy_shim_headers "${SWIFTLIB_DIR}/shims"
252-
section_magic
253252
${GROUP_INFO_JSON_FILE}
254253
SWIFT_COMPILE_FLAGS ${swift_stdlib_compile_flags}
255254
LINK_FLAGS ${swift_core_link_flags}

0 commit comments

Comments
 (0)