[lld] 6881f29 - [lld-macho] Parse re-exports of nested TAPI documents
Jez Ng via llvm-commits
llvm-commits at lists.llvm.org
Thu Jun 3 09:02:39 PDT 2021
Author: Jez Ng
Date: 2021-06-03T12:02:30-04:00
New Revision: 6881f29a36a97102e5c89653a343f656231bc2f2
URL: https://github.com/llvm/llvm-project/commit/6881f29a36a97102e5c89653a343f656231bc2f2
DIFF: https://github.com/llvm/llvm-project/commit/6881f29a36a97102e5c89653a343f656231bc2f2.diff
LOG: [lld-macho] Parse re-exports of nested TAPI documents
D103423 neglected to call `parseReexports()` for nested TBD
documents, leading to symbol resolution failures when trying to look up
a symbol nested more than one level deep in a TBD file. This fixes the
regression and adds a test.
It also appears that `umbrella` wasn't being set properly when calling
`parseLoadCommands` -- it's supposed to resolve to `this` if `nullptr`
is passed. I didn't write a failing test case for this but I've made
`umbrella` a member so the previous behavior should be preserved.
Reviewed By: #lld-macho, thakis
Differential Revision: https://reviews.llvm.org/D103586
Added:
Modified:
lld/MachO/DriverUtils.cpp
lld/MachO/InputFiles.cpp
lld/MachO/InputFiles.h
lld/test/MachO/tapi-link.s
Removed:
################################################################################
diff --git a/lld/MachO/DriverUtils.cpp b/lld/MachO/DriverUtils.cpp
index 457c3c643ae2d..01b174297e525 100644
--- a/lld/MachO/DriverUtils.cpp
+++ b/lld/MachO/DriverUtils.cpp
@@ -234,7 +234,7 @@ DylibFile *macho::loadDylib(MemoryBufferRef mbref, DylibFile *umbrella,
// in previous block for why this means we must copy `file` here.
newFile = file;
if (newFile->exportingFile)
- newFile->parseLoadCommands(mbref, umbrella);
+ newFile->parseLoadCommands(mbref);
}
return newFile;
}
diff --git a/lld/MachO/InputFiles.cpp b/lld/MachO/InputFiles.cpp
index 15dffab485896..5aedf003458f9 100644
--- a/lld/MachO/InputFiles.cpp
+++ b/lld/MachO/InputFiles.cpp
@@ -766,8 +766,11 @@ DylibFile *findDylib(StringRef path, DylibFile *umbrella,
for (InterfaceFile &child :
make_pointee_range(currentTopLevelTapi->documents())) {
assert(child.documents().empty());
- if (path == child.getInstallName())
- return make<DylibFile>(child, umbrella);
+ if (path == child.getInstallName()) {
+ auto file = make<DylibFile>(child, umbrella);
+ file->parseReexports(child);
+ return file;
+ }
}
}
@@ -813,6 +816,7 @@ DylibFile::DylibFile(MemoryBufferRef mb, DylibFile *umbrella,
assert(!isBundleLoader || !umbrella);
if (umbrella == nullptr)
umbrella = this;
+ this->umbrella = umbrella;
auto *buf = reinterpret_cast<const uint8_t *>(mb.getBufferStart());
auto *hdr = reinterpret_cast<const mach_header *>(mb.getBufferStart());
@@ -839,7 +843,7 @@ DylibFile::DylibFile(MemoryBufferRef mb, DylibFile *umbrella,
return;
// Initialize symbols.
- exportingFile = isImplicitlyLinked(dylibName) ? this : umbrella;
+ exportingFile = isImplicitlyLinked(dylibName) ? this : this->umbrella;
if (const load_command *cmd = findCommand(hdr, LC_DYLD_INFO_ONLY)) {
auto *c = reinterpret_cast<const dyld_info_command *>(cmd);
parseTrie(buf + c->export_off, c->export_size,
@@ -855,7 +859,7 @@ DylibFile::DylibFile(MemoryBufferRef mb, DylibFile *umbrella,
}
}
-void DylibFile::parseLoadCommands(MemoryBufferRef mb, DylibFile *umbrella) {
+void DylibFile::parseLoadCommands(MemoryBufferRef mb) {
auto *hdr = reinterpret_cast<const mach_header *>(mb.getBufferStart());
const uint8_t *p = reinterpret_cast<const uint8_t *>(mb.getBufferStart()) +
target->headerSize;
@@ -902,6 +906,7 @@ DylibFile::DylibFile(const InterfaceFile &interface, DylibFile *umbrella,
if (umbrella == nullptr)
umbrella = this;
+ this->umbrella = umbrella;
dylibName = saver.save(interface.getInstallName());
compatibilityVersion = interface.getCompatibilityVersion().rawValue();
@@ -949,7 +954,7 @@ DylibFile::DylibFile(const InterfaceFile &interface, DylibFile *umbrella,
}
}
-void DylibFile::parseReexports(const llvm::MachO::InterfaceFile &interface) {
+void DylibFile::parseReexports(const InterfaceFile &interface) {
const InterfaceFile *topLevel =
interface.getParent() == nullptr ? &interface : interface.getParent();
for (InterfaceFileRef intfRef : interface.reexportedLibraries()) {
diff --git a/lld/MachO/InputFiles.h b/lld/MachO/InputFiles.h
index c26cd0f976221..5665ee20a6419 100644
--- a/lld/MachO/InputFiles.h
+++ b/lld/MachO/InputFiles.h
@@ -144,13 +144,14 @@ class DylibFile : public InputFile {
// the root dylib to ensure symbols in the child library are correctly bound
// to the root. On the other hand, if a dylib is being directly loaded
// (through an -lfoo flag), then `umbrella` should be a nullptr.
- void parseLoadCommands(MemoryBufferRef mb, DylibFile *umbrella);
+ void parseLoadCommands(MemoryBufferRef mb);
void parseReexports(const llvm::MachO::InterfaceFile &interface);
static bool classof(const InputFile *f) { return f->kind() == DylibKind; }
StringRef dylibName;
DylibFile *exportingFile = nullptr;
+ DylibFile *umbrella;
uint32_t compatibilityVersion = 0;
uint32_t currentVersion = 0;
int64_t ordinal = 0; // Ordinal numbering starts from 1, so 0 is a sentinel
diff --git a/lld/test/MachO/tapi-link.s b/lld/test/MachO/tapi-link.s
index c83c149d5b830..c43963c280e61 100644
--- a/lld/test/MachO/tapi-link.s
+++ b/lld/test/MachO/tapi-link.s
@@ -1,16 +1,16 @@
# REQUIRES: x86
-# RUN: mkdir -p %t
-#
-# RUN: llvm-mc -filetype obj -triple x86_64-apple-darwin %s -o %t/test.o
+# RUN: split-file %s %t --no-leading-lines
-# RUN: %lld -o %t/test -lSystem -lc++ -framework CoreFoundation %t/test.o
+# RUN: llvm-mc -filetype obj -triple x86_64-apple-darwin %t/test.s -o %t/test.o
+
+# RUN: %lld -o %t/test -lSystem -lc++ -framework CoreFoundation %t/libNested.tbd %t/test.o
# RUN: llvm-objdump --bind --no-show-raw-insn -d -r %t/test | FileCheck %s
## libReexportSystem.tbd tests that we can reference symbols from a dylib,
## re-exported by a top-level tapi document, which itself is re-exported by
## another top-level tapi document.
-# RUN: %lld -o %t/with-reexport %S/Inputs/libReexportSystem.tbd -lc++ -framework CoreFoundation %t/test.o
+# RUN: %lld -o %t/with-reexport %S/Inputs/libReexportSystem.tbd -lc++ -framework CoreFoundation %t/libNested.tbd %t/test.o
# RUN: llvm-objdump --bind --no-show-raw-insn -d -r %t/with-reexport | FileCheck %s
# CHECK: Disassembly of section __TEXT,__text:
@@ -23,6 +23,7 @@
# CHECK-DAG: __DATA __data {{.*}} pointer 0 CoreFoundation _OBJC_IVAR_$_NSConstantArray._count
# CHECK-DAG: __DATA __data {{.*}} pointer 0 CoreFoundation _OBJC_EHTYPE_$_NSException
# CHECK-DAG: __DATA __data {{.*}} pointer 0 libc++abi ___gxx_personality_v0
+# CHECK-DAG: __DATA __data {{.*}} pointer 0 libNested3 _deeply_nested
# RUN: llvm-objdump --macho --all-headers %t/test | \
# RUN: FileCheck --check-prefix=LOAD %s
@@ -44,6 +45,7 @@
# LOAD-REEXPORT-NEXT: current version 1.0.0
# LOAD-REEXPORT-NEXT: compatibility version
+#--- test.s
.section __TEXT,__text
.global _main
@@ -57,9 +59,39 @@ _main:
.quad _OBJC_METACLASS_$_NSObject
.quad _OBJC_IVAR_$_NSConstantArray._count
.quad _OBJC_EHTYPE_$_NSException
+ .quad _deeply_nested
## This symbol is defined in libc++abi.tbd, but we are linking test.o against
## libc++.tbd (which re-exports libc++abi). Linking against this symbol verifies
## that .tbd file re-exports can refer not just to TAPI documents within the
## same .tbd file, but to other on-disk files as well.
.quad ___gxx_personality_v0
+
+## This tests that we can locate a symbol re-exported by a child of a TAPI
+## document.
+#--- libNested.tbd
+--- !tapi-tbd-v3
+archs: [ x86_64 ]
+uuids: [ 'x86_64: 00000000-0000-0000-0000-000000000000' ]
+platform: macosx
+install-name: '/usr/lib/libNested.dylib'
+exports:
+ - archs: [ x86_64 ]
+ re-exports: [ '/usr/lib/libNested2.dylib' ]
+--- !tapi-tbd-v3
+archs: [ x86_64 ]
+uuids: [ 'x86_64: 00000000-0000-0000-0000-000000000001' ]
+platform: macosx
+install-name: '/usr/lib/libNested2.dylib'
+exports:
+ - archs: [ x86_64 ]
+ re-exports: [ '/usr/lib/libNested3.dylib' ]
+--- !tapi-tbd-v3
+archs: [ x86_64 ]
+uuids: [ 'x86_64: 00000000-0000-0000-0000-000000000002' ]
+platform: macosx
+install-name: '/usr/lib/libNested3.dylib'
+exports:
+ - archs: [ x86_64 ]
+ symbols: [ _deeply_nested ]
+...
More information about the llvm-commits
mailing list