[lld] [lld][MachO] Implement -emit-tbd-only= (PR #194899)
via llvm-commits
llvm-commits at lists.llvm.org
Tue May 5 10:50:12 PDT 2026
llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-lld-macho
Author: Nuri Amari (NuriAmari)
<details>
<summary>Changes</summary>
This extends lld for MachO with a flag that when passed signals to the linker to produce a tbd to represent the dylib it would normally produce, rather actually producing the dylib.
This can be used to allow long dependent links to proceed in parralel to a larger degree. Producing a tbd for a dylib is much faster than actually producing the dylib in most cases, especially for LTO links.
With this flag, one can instruct the build system to create two linker invocations for each dylib built. One will actually build the link unit, the other will produce the tbd, but much faster. Dependent link jobs can then begin as soon as the tbd is ready (linking against the tbd instead of the dylib itself), while the expensive LTO link itself may continue to run in parrallel.
Using tbd files as an interface for dylibs also has the advantage of invalidating dependent links less often. For example, if the body of a function changes, the tbd for the link unit will not change, but the link unit itself will.
There are existing tools to produce tbd files, but none can produce them as accurately and as quickly. Some compilers may emit tbd files that represent individual translation units, but they are likely to be incorrect. This is the final tbd depends on symbol resolution done by the linker, which is sensitive to factors like object file input order. TAPI related tools can generate a tbd from an existing dylib, but that does not provide the parralelism advantages, you have to complete the link first in order to produce the tbd.
---
Patch is 30.37 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/194899.diff
18 Files Affected:
- (modified) lld/MachO/Config.h (+1)
- (modified) lld/MachO/Driver.cpp (+87-5)
- (modified) lld/MachO/InputFiles.cpp (+2-1)
- (modified) lld/MachO/LTO.cpp (+60-4)
- (modified) lld/MachO/LTO.h (+1-1)
- (modified) lld/MachO/Options.td (+4)
- (modified) lld/MachO/SymbolTable.cpp (+2-2)
- (modified) lld/MachO/SymbolTable.h (+2-1)
- (modified) lld/MachO/Symbols.cpp (+8-4)
- (modified) lld/MachO/Symbols.h (+4-1)
- (modified) lld/test/CMakeLists.txt (+1)
- (modified) lld/test/MachO/Inputs/iPhoneSimulator.sdk/usr/lib/libSystem.tbd (+16-3)
- (added) lld/test/MachO/emit-tbd/bitcode-basic.ll (+84)
- (added) lld/test/MachO/emit-tbd/exported-symbols.ll (+21)
- (added) lld/test/MachO/emit-tbd/native-basic.s (+35)
- (added) lld/test/MachO/emit-tbd/strong-weak-conflict.s (+54)
- (added) lld/test/MachO/emit-tbd/thread-local.s (+32)
- (added) lld/test/MachO/emit-tbd/visibility-conflict.ll (+33)
``````````diff
diff --git a/lld/MachO/Config.h b/lld/MachO/Config.h
index 9767cc5e5b6e4..58b72077de30a 100644
--- a/lld/MachO/Config.h
+++ b/lld/MachO/Config.h
@@ -177,6 +177,7 @@ struct Configuration {
llvm::CachePruningPolicy thinLTOCachePolicy;
llvm::StringRef thinLTOCacheDir;
llvm::StringRef thinLTOIndexOnlyArg;
+ llvm::StringRef emitTBDPath;
std::pair<llvm::StringRef, llvm::StringRef> thinLTOObjectSuffixReplace;
llvm::StringRef thinLTOPrefixReplaceOld;
llvm::StringRef thinLTOPrefixReplaceNew;
diff --git a/lld/MachO/Driver.cpp b/lld/MachO/Driver.cpp
index 26b39f7a28d0d..a6001f1b18fcf 100644
--- a/lld/MachO/Driver.cpp
+++ b/lld/MachO/Driver.cpp
@@ -53,6 +53,8 @@
#include "llvm/TargetParser/Host.h"
#include "llvm/TextAPI/Architecture.h"
#include "llvm/TextAPI/PackedVersion.h"
+#include "llvm/TextAPI/Target.h"
+#include "llvm/TextAPI/TextAPIWriter.h"
#if !_WIN32
#include <sys/mman.h>
@@ -554,7 +556,7 @@ static InputFile *processFile(std::optional<MemoryBufferRef> buffer,
if (newFile && !isa<DylibFile>(newFile)) {
if ((isa<ObjFile>(newFile) || isa<BitcodeFile>(newFile)) && newFile->lazy &&
config->forceLoadObjC) {
- for (Symbol *sym : newFile->symbols)
+ for (lld::macho::Symbol *sym : newFile->symbols)
if (sym && sym->getName().starts_with(objc::symbol_names::klass)) {
extract(*newFile, "-ObjC");
break;
@@ -773,7 +775,7 @@ static bool compileBitcodeFiles() {
static void replaceCommonSymbols() {
TimeTraceScope timeScope("Replace common symbols");
ConcatOutputSection *osec = nullptr;
- for (Symbol *sym : symtab->getSymbols()) {
+ for (lld::macho::Symbol *sym : symtab->getSymbols()) {
auto *common = dyn_cast<CommonSymbol>(sym);
if (common == nullptr)
continue;
@@ -1551,7 +1553,7 @@ static void foldIdenticalLiterals() {
static void addSynthenticMethnames() {
std::string &data = *make<std::string>();
llvm::raw_string_ostream os(data);
- for (Symbol *sym : symtab->getSymbols())
+ for (lld::macho::Symbol *sym : symtab->getSymbols())
if (isa<Undefined>(sym))
if (ObjCStubsSection::isObjCStubSymbol(sym))
os << ObjCStubsSection::getMethname(sym) << '\0';
@@ -1638,7 +1640,8 @@ static void handleExplicitExports() {
static constexpr int kMaxWarnings = 3;
if (config->hasExplicitExports) {
std::atomic<uint64_t> warningsCount{0};
- parallelForEach(symtab->getSymbols(), [&warningsCount](Symbol *sym) {
+ parallelForEach(symtab->getSymbols(), [&warningsCount](
+ lld::macho::Symbol *sym) {
if (auto *defined = dyn_cast<Defined>(sym)) {
if (config->exportedSymbols.match(sym->getName())) {
if (defined->privateExtern) {
@@ -1668,7 +1671,7 @@ static void handleExplicitExports() {
warn("<... " + Twine(warningsCount - kMaxWarnings) +
" more similar warnings...>");
} else if (!config->unexportedSymbols.empty()) {
- parallelForEach(symtab->getSymbols(), [](Symbol *sym) {
+ parallelForEach(symtab->getSymbols(), [](lld::macho::Symbol *sym) {
if (auto *defined = dyn_cast<Defined>(sym))
if (config->unexportedSymbols.match(defined->getName()))
defined->privateExtern = true;
@@ -1706,6 +1709,73 @@ static SmallVector<StringRef, 0> getAllowableClients(opt::InputArgList &args) {
return vals;
}
+static void resolveBitcodeProvidedSymbolsForTBDGeneration() {
+ auto *lto = make<BitcodeCompiler>();
+ for (InputFile *file : inputFiles)
+ if (auto *bitcodeFile = dyn_cast<BitcodeFile>(file))
+ if (!file->lazy)
+ lto->add(*bitcodeFile, /* forTBDGeneration */ true);
+}
+
+static void writeTBD(const StringRef outputPath) {
+ std::error_code errorCode;
+ llvm::raw_fd_ostream os(outputPath, errorCode, llvm::sys::fs::OF_Text);
+ if (errorCode) {
+ error("Failed to open stream to write tbd to: '" + outputPath + "' " +
+ errorCode.message());
+ return;
+ }
+
+ Triple targetTriple =
+ Triple(getTargetTripleName(config->platformInfo.target));
+ std::shared_ptr<MachO::RecordsSlice> records =
+ std::make_shared<MachO::RecordsSlice>(targetTriple);
+ auto &binaryAttributes = records->getBinaryAttrs();
+ binaryAttributes.InstallName = config->installName;
+ binaryAttributes.AppExtensionSafe = config->applicationExtension;
+ binaryAttributes.TwoLevelNamespace =
+ config->namespaceKind == NamespaceKind::twolevel;
+
+ for (const lld::macho::Symbol *symbol : symtab->getSymbols()) {
+ if (const lld::macho::Defined *definedSymbol = dyn_cast<Defined>(symbol)) {
+ MachO::RecordLinkage symbolLinkage = MachO::RecordLinkage::Unknown;
+ MachO::SymbolFlags symbolFlags = MachO::SymbolFlags::None;
+
+ if (definedSymbol->weakDefCanBeHidden)
+ continue;
+
+ if (!definedSymbol->isExternal())
+ continue;
+
+ if (!definedSymbol->includeInSymtab)
+ continue;
+
+ if (definedSymbol->privateExtern)
+ continue;
+
+ symbolLinkage = MachO::RecordLinkage::Exported;
+
+ if (definedSymbol->isTlv())
+ symbolFlags |= MachO::SymbolFlags::ThreadLocalValue;
+ else if (definedSymbol->isWeakDef())
+ symbolFlags |= MachO::SymbolFlags::WeakDefined;
+
+ records->addRecord(definedSymbol->getName(), symbolFlags,
+ MachO::GlobalRecord::Kind::Unknown, symbolLinkage);
+ }
+ }
+
+ std::unique_ptr<MachO::InterfaceFile> interface =
+ MachO::convertToInterfaceFile({records});
+ Error e = MachO::TextAPIWriter::writeToStream(os, *interface,
+ MachO::FileType::TBD_V4);
+ if (e) {
+ error("Failed to write resulting tbd to: '" + outputPath +
+ "': " + toString(std::move(e)));
+ return;
+ }
+}
+
namespace lld {
namespace macho {
bool link(ArrayRef<const char *> argsArr, llvm::raw_ostream &stdoutOS,
@@ -1938,6 +2008,7 @@ bool link(ArrayRef<const char *> argsArr, llvm::raw_ostream &stdoutOS,
config->thinLTOIndexOnly = args.hasArg(OPT_thinlto_index_only) ||
args.hasArg(OPT_thinlto_index_only_eq);
config->thinLTOIndexOnlyArg = args.getLastArgValue(OPT_thinlto_index_only_eq);
+ config->emitTBDPath = args.getLastArgValue(OPT_emit_tbd_only_eq);
config->thinLTOObjectSuffixReplace =
getOldNewOptions(args, OPT_thinlto_object_suffix_replace_eq);
std::tie(config->thinLTOPrefixReplaceOld, config->thinLTOPrefixReplaceNew,
@@ -2392,6 +2463,16 @@ bool link(ArrayRef<const char *> argsArr, llvm::raw_ostream &stdoutOS,
// optimize.
handleExplicitExports();
+ if (!config->emitTBDPath.empty()) {
+ // If we want to write a TBD, we need to finalize the symbol table before
+ // we do so.
+ resolveBitcodeProvidedSymbolsForTBDGeneration();
+ handleExplicitExports();
+ replaceCommonSymbols();
+ writeTBD(config->emitTBDPath);
+ return errorCount() == 0;
+ }
+
bool didCompileBitcodeFiles = compileBitcodeFiles();
resolveLCLinkerOptions();
@@ -2495,5 +2576,6 @@ bool link(ArrayRef<const char *> argsArr, llvm::raw_ostream &stdoutOS,
return errorCount() == 0;
}
+
} // namespace macho
} // namespace lld
diff --git a/lld/MachO/InputFiles.cpp b/lld/MachO/InputFiles.cpp
index 73b2d47d69a72..de54bede91232 100644
--- a/lld/MachO/InputFiles.cpp
+++ b/lld/MachO/InputFiles.cpp
@@ -2342,7 +2342,8 @@ static macho::Symbol *createBitcodeSymbol(const lto::InputFile::Symbol &objSym,
/*size=*/0, objSym.isWeak(), isPrivateExtern,
/*isReferencedDynamically=*/false,
/*noDeadStrip=*/false,
- /*isWeakDefCanBeHidden=*/false);
+ /*isWeakDefCanBeHidden=*/false,
+ /*isTlv*/ objSym.isTLS());
}
BitcodeFile::BitcodeFile(MemoryBufferRef mb, StringRef archiveName,
diff --git a/lld/MachO/LTO.cpp b/lld/MachO/LTO.cpp
index c8b7a4e797250..67a0b2b496821 100644
--- a/lld/MachO/LTO.cpp
+++ b/lld/MachO/LTO.cpp
@@ -118,7 +118,7 @@ BitcodeCompiler::BitcodeCompiler() {
ltoObj = std::make_unique<lto::LTO>(createConfig(), backend);
}
-void BitcodeCompiler::add(BitcodeFile &f) {
+void BitcodeCompiler::add(BitcodeFile &f, bool forTBDGeneration) {
lto::InputFile &obj = *f.obj;
if (config->thinLTOEmitIndexFiles)
@@ -159,9 +159,65 @@ void BitcodeCompiler::add(BitcodeFile &f) {
// Un-define the symbol so that we don't get duplicate symbol errors when we
// load the ObjFile emitted by LTO compilation.
- if (r.Prevailing)
- replaceSymbol<Undefined>(sym, sym->getName(), sym->getFile(),
- RefState::Strong, /*wasBitcodeSymbol=*/true);
+ if (r.Prevailing) {
+ // Symbol resolution for bitcode provided symbols works slightly
+ // differently from symbol resolution for native symbols. For
+ // every symbol occurence (the same symbol name may occur multiple times),
+ // a prevailing copy is chosen. In an ordinary LTO link, we remove this
+ // symbol from the symbol table below, replacing it with an undefined
+ // reference. We then compile each bitcode file, and once we have native
+ // object files, we add those symbols back into the symbol table at that
+ // time. At that point, each symbol name is unique as non-prevailing
+ // copies will be dropped by the LTO backend. For the purposes of
+ // generating a TBD, we want the symbol table to appear as it would after
+ // LTO is complete, without actually performing LTO. If we are generating
+ // a TBD, instead of replacing prevailing symbols with an undefined
+ // reference, we insert into the symbol table a symbol with attributes
+ // derived from the prevailing IR symbol. Note that this is slightly
+ // different from how native symbol resolution works amid ODR violations.
+ // In such case symbol attributes such as weakness and visibility
+ // can be "merged" (ie. the symbol is strong if any copy is strong).
+ // This is not how LTO symbol resolution works, we choose a prevailing
+ // copy, and take all its attributes wholesale, there is no merging of
+ // attributes with non-prevailing copies.
+ if (forTBDGeneration) {
+ bool isPrivateExtern = false;
+ switch (objSym.getVisibility()) {
+ case GlobalValue::HiddenVisibility:
+ isPrivateExtern = true;
+ break;
+ case GlobalValue::ProtectedVisibility:
+ error(sym->getName() +
+ " has protected visibility, which is not supported by Mach-O");
+ break;
+ case GlobalValue::DefaultVisibility:
+ break;
+ }
+ isPrivateExtern = isPrivateExtern ||
+ objSym.canBeOmittedFromSymbolTable() || f.forceHidden;
+
+ if (const auto *defined = dyn_cast<Defined>(sym)) {
+
+ bool interposable = config->namespaceKind == NamespaceKind::flat &&
+ config->outputType != MachO::MH_EXECUTE &&
+ !isPrivateExtern;
+
+ replaceSymbol<Defined>(
+ sym, defined->getName(), &f, /*isec*/ nullptr, /*value*/ 0,
+ /*size*/ 0, objSym.isWeak(), /*isExternal*/ true, isPrivateExtern,
+ /* includeInSymtab */ true,
+ /* isReferencedDynamically */ false, /* noDeadStrip */ false,
+ /* canOverrideWeakDef */ false, /* isWeakDefCanBeHidden */ false,
+ interposable, /* isTlv */ objSym.isTLS());
+ } else if (const auto *common = dyn_cast<CommonSymbol>(sym)) {
+ replaceSymbol<CommonSymbol>(
+ sym, common->getName(), &f, objSym.getCommonSize(),
+ objSym.getCommonAlignment(), isPrivateExtern);
+ }
+ } else
+ replaceSymbol<Undefined>(sym, sym->getName(), sym->getFile(),
+ RefState::Strong, /*wasBitcodeSymbol=*/true);
+ }
// TODO: set the other resolution configs properly
}
diff --git a/lld/MachO/LTO.h b/lld/MachO/LTO.h
index 86c39b1450703..0203ff2390a3a 100644
--- a/lld/MachO/LTO.h
+++ b/lld/MachO/LTO.h
@@ -30,7 +30,7 @@ class BitcodeCompiler {
public:
BitcodeCompiler();
- void add(BitcodeFile &f);
+ void add(BitcodeFile &f, bool forTBDGeneration = false);
std::vector<ObjFile *> compile();
private:
diff --git a/lld/MachO/Options.td b/lld/MachO/Options.td
index b7686d66a258e..2f6ad7f780c32 100644
--- a/lld/MachO/Options.td
+++ b/lld/MachO/Options.td
@@ -216,6 +216,10 @@ defm pgo_warn_mismatch: BB<"pgo-warn-mismatch",
defm warn_thin_archive_missing_members : BB<"warn-thin-archive-missing-members",
"Warn on missing object files referenced by thin archives (default)",
"Do not warn on missing object files referenced by thin archives">, Group<grp_lld>;
+def emit_tbd_only_eq : Joined<["--"], "emit-tbd-only=">,
+ HelpText<"Generate a tbd which represents the link "
+ "unit, rather than producing a link unit">,
+ Group<grp_lld>;
// This is a complete Options.td compiled from Apple's ld(1) manpage
// dated 2018-03-07 and cross checked with ld64 source code in repo
diff --git a/lld/MachO/SymbolTable.cpp b/lld/MachO/SymbolTable.cpp
index 84d3e45d64396..ef55cf2a3212f 100644
--- a/lld/MachO/SymbolTable.cpp
+++ b/lld/MachO/SymbolTable.cpp
@@ -104,7 +104,7 @@ Defined *SymbolTable::addDefined(StringRef name, InputFile *file,
uint64_t size, bool isWeakDef,
bool isPrivateExtern,
bool isReferencedDynamically, bool noDeadStrip,
- bool isWeakDefCanBeHidden) {
+ bool isWeakDefCanBeHidden, bool isTlv) {
bool overridesWeakDef = false;
auto [s, wasInserted] = insert(name, file);
@@ -211,7 +211,7 @@ Defined *SymbolTable::addDefined(StringRef name, InputFile *file,
Defined *defined = replaceSymbol<Defined>(
s, name, file, isec, value, size, isWeakDef, /*isExternal=*/true,
isPrivateExtern, /*includeInSymtab=*/true, isReferencedDynamically,
- noDeadStrip, overridesWeakDef, isWeakDefCanBeHidden, interposable);
+ noDeadStrip, overridesWeakDef, isWeakDefCanBeHidden, interposable, isTlv);
return defined;
}
diff --git a/lld/MachO/SymbolTable.h b/lld/MachO/SymbolTable.h
index e9b03da9d2549..bf94799996837 100644
--- a/lld/MachO/SymbolTable.h
+++ b/lld/MachO/SymbolTable.h
@@ -39,7 +39,8 @@ class SymbolTable {
Defined *addDefined(StringRef name, InputFile *, InputSection *,
uint64_t value, uint64_t size, bool isWeakDef,
bool isPrivateExtern, bool isReferencedDynamically,
- bool noDeadStrip, bool isWeakDefCanBeHidden);
+ bool noDeadStrip, bool isWeakDefCanBeHidden,
+ bool isTlv = false);
Defined *aliasDefined(Defined *src, StringRef target, InputFile *newFile,
bool makePrivateExtern = false);
diff --git a/lld/MachO/Symbols.cpp b/lld/MachO/Symbols.cpp
index 9faf01e09de05..38d82ae6557d7 100644
--- a/lld/MachO/Symbols.cpp
+++ b/lld/MachO/Symbols.cpp
@@ -21,7 +21,7 @@ static_assert(sizeof(void *) != 8 || sizeof(Symbol) == 56,
// The Microsoft ABI doesn't support using parent class tail padding for child
// members, hence the _MSC_VER check.
#if !defined(_MSC_VER)
-static_assert(sizeof(void *) != 8 || sizeof(Defined) == 88,
+static_assert(sizeof(void *) != 8 || sizeof(Defined) == 96,
"Try to minimize Defined's size; we create many instances");
#endif
@@ -57,14 +57,14 @@ Defined::Defined(StringRef name, InputFile *file, InputSection *isec,
bool isPrivateExtern, bool includeInSymtab,
bool isReferencedDynamically, bool noDeadStrip,
bool canOverrideWeakDef, bool isWeakDefCanBeHidden,
- bool interposable)
+ bool interposable, bool isTlv)
: Symbol(DefinedKind, name, file), overridesWeakDef(canOverrideWeakDef),
privateExtern(isPrivateExtern), includeInSymtab(includeInSymtab),
identicalCodeFoldingKind(ICFFoldKind::None),
referencedDynamically(isReferencedDynamically), noDeadStrip(noDeadStrip),
interposable(interposable), weakDefCanBeHidden(isWeakDefCanBeHidden),
weakDef(isWeakDef), external(isExternal), originalIsec(isec),
- value(value), size(size) {
+ value(value), size(size), tlv(isTlv) {
if (isec) {
isec->symbols.push_back(this);
// Maintain sorted order.
@@ -82,7 +82,11 @@ Defined::Defined(StringRef name, InputFile *file, InputSection *isec,
}
bool Defined::isTlv() const {
- return !isAbsolute() && isThreadLocalVariables(originalIsec->getFlags());
+ if (!isAbsolute()) {
+ return isThreadLocalVariables(originalIsec->getFlags());
+ }
+
+ return tlv;
}
uint64_t Defined::getVA() const {
diff --git a/lld/MachO/Symbols.h b/lld/MachO/Symbols.h
index beb97b35bf881..0cceb7f26ec3b 100644
--- a/lld/MachO/Symbols.h
+++ b/lld/MachO/Symbols.h
@@ -118,7 +118,7 @@ class Defined : public Symbol {
uint64_t size, bool isWeakDef, bool isExternal, bool isPrivateExtern,
bool includeInSymtab, bool isReferencedDynamically, bool noDeadStrip,
bool canOverrideWeakDef = false, bool isWeakDefCanBeHidden = false,
- bool interposable = false);
+ bool interposable = false, bool isTlv = false);
bool isWeakDef() const override { return weakDef; }
bool isExternalWeakDef() const {
@@ -194,6 +194,9 @@ class Defined : public Symbol {
uint64_t size;
// This can be a subsection of either __compact_unwind or __eh_frame.
ConcatInputSection *originalUnwindEntry = nullptr;
+
+private:
+ const bool tlv : 1;
};
// This enum does double-duty: as a symbol property, it indicates whether & how
diff --git a/lld/test/CMakeLists.txt b/lld/test/CMakeLists.txt
index 1bd3ad7e1765b..73c0a4cb2f7b8 100644
--- a/lld/test/CMakeLists.txt
+++ b/lld/test/CMakeLists.txt
@@ -66,6 +66,7 @@ if (NOT LLD_BUILT_STANDALONE)
llvm-profdata
llvm-readelf
llvm-readobj
+ llvm-readtapi
llvm-strings
llvm-strip
llvm-symbolizer
diff --git a/lld/test/MachO/Inputs/iPhoneSimulator.sdk/usr/lib/libSystem.tbd b/lld/test/MachO/Inputs/iPhoneSimulator.sdk/usr/lib/libSystem.tbd
index f1f1dc7aaa140..b10c67ab728e4 100644
--- a/lld/test/MachO/Inputs/iPhoneSimulator.sdk/usr/lib/libSystem.tbd
+++ b/lld/test/MachO/Inputs/iPhoneSimulator.sdk/usr/lib/libSystem.tbd
@@ -9,6 +9,7 @@ current-version: 1281
exports:
- archs: [ i386, x86_64, arm64 ]
re-exports: [ '/usr/lib/system/libcache.dylib',
+ '/usr/lib/system/libdyld.dylib',
'/usr/lib/system/libsystem_kernel.dylib' ]
symbols: [ __crashreporter_info__, _cache_create, dyld_stub_binder ]
--- !tapi-tbd-v3
@@ -37,15 +38,27 @@ parent-umbrella: System
exports:
- archs: [ i386, x86_64, arm64 ]
symbols: [ ___fsync ]
-
-# The following TAPI document is not re-exported by any other document in this
-# TBD file, and should therefore be inaccessible.
--- !tapi-tbd-v3
archs: [ i386, x86_64, arm64 ]
uuids: [ 'i386: 00000000-0000-0000-0000-000000000006',
'x86_64: 00000000-0000-0000-0000-000000000007',
'arm64: 00000000-0000-0000-0000-000000000008' ]
platform: ios
+install-name: '/usr/lib/system/libdyld.dylib'
+current-version: 83
+parent-umbrella: System
+exports:
+ - archs: [ i386, x86_64, arm64 ]
+ symbols: [ __tlv_bootstrap ]
+
+# The following TAPI document is not re-exported by any other document in this
+# TBD file, and should therefore be inaccessible.
+--- !tapi-tbd-v3
+archs: [ i386, x86_64, arm64 ]
+uuids: [ 'i386: 00000000-0000-0000-0000-000000000009',
+ 'x86_64: 00000000-0000-0000-0000-000000000010',
+ 'arm64: 00000000-0000-0000-0000-000000000011' ]
+platform: ios
install-name: '/usr/lib/libnotreexported.dylib'
exports:
- archs: [ i386, x86_64, arm64 ]
diff --git a/lld/test/MachO/emit-tbd/bitcode-basic.ll b/lld/test/MachO/emit-tbd/bitcode-basic.ll
new file mode 100644
index 0000000000000..cecf2c145d811
...
[truncated]
``````````
</details>
https://github.com/llvm/llvm-project/pull/194899
More information about the llvm-commits
mailing list