[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