[PATCH] D83925: [lld-macho] Support lookup of dylibs in frameworks

Jez Ng via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Wed Jul 15 19:13:33 PDT 2020


int3 created this revision.
int3 added a reviewer: lld-macho.
Herald added a project: LLVM.
Herald added a subscriber: llvm-commits.

Needed for testing Objective-C programs (since e.g. Core
Foundation is a framework)


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D83925

Files:
  lld/MachO/Driver.cpp
  lld/test/MachO/framework.s


Index: lld/test/MachO/framework.s
===================================================================
--- /dev/null
+++ lld/test/MachO/framework.s
@@ -0,0 +1,29 @@
+# REQUIRES: x86
+# RUN: mkdir -p %t
+# RUN: echo ".globl _foo; _foo: ret" | llvm-mc -filetype=obj -triple=x86_64-apple-darwin -o %t/foo.o
+# RUN: mkdir -p %t/Foo.framework/Versions/A
+# RUN: lld -flavor darwinnew -L%S/Inputs/MacOSX.sdk/usr/lib -dylib -install_name %t/Foo.framework/Versions/A/Foo %t/foo.o -o %t/Foo.framework/Versions/A/Foo
+# RUN: lld -flavor darwinnew -L%S/Inputs/MacOSX.sdk/usr/lib -dylib -install_name %t/Foo.framework/Versions/A/Foobar %t/foo.o -o %t/Foo.framework/Versions/A/Foobar
+# RUN: ln -sf %t/Foo.framework/Versions/A %t/Foo.framework/Versions/Current
+# RUN: ln -sf %t/Foo.framework/Versions/Current/Foo %t/Foo.framework/Foo
+
+# RUN: llvm-mc -filetype=obj -triple=x86_64-apple-darwin -o %t/test.o %s
+# RUN: lld -flavor darwinnew -L%S/Inputs/MacOSX.sdk/usr/lib -lSystem -F%t -framework Foo %t/test.o -o %t/test
+# RUN: llvm-objdump --macho --lazy-bind %t/test | FileCheck %s --check-prefix=NOSUFFIX
+# NOSUFFIX: __DATA __la_symbol_ptr 0x{{[0-9a-f]*}} {{.*}}Foo _foo
+
+# RUN: lld -flavor darwinnew -L%S/Inputs/MacOSX.sdk/usr/lib -lSystem -F%t -framework Foo,baz %t/test.o -o %t/test-wrong-suffix
+# RUN: llvm-objdump --macho --lazy-bind %t/test-wrong-suffix | FileCheck %s --check-prefix=NOSUFFIX
+
+# RUN: lld -flavor darwinnew -L%S/Inputs/MacOSX.sdk/usr/lib -lSystem -F%t -framework Foo,bar %t/test.o -o %t/test-suffix
+# RUN: llvm-objdump --macho --lazy-bind %t/test-suffix | FileCheck %s --check-prefix=SUFFIX
+# SUFFIX: __DATA __la_symbol_ptr 0x{{[0-9a-f]*}} {{.*}}Foobar _foo
+
+.globl _main
+.text
+_main:
+  sub $8, %rsp # 16-byte-align the stack; dylld -flavor darwinnew checks for this
+  callq _foo
+  mov $0, %rax
+  add $8, %rsp
+  ret
Index: lld/MachO/Driver.cpp
===================================================================
--- lld/MachO/Driver.cpp
+++ lld/MachO/Driver.cpp
@@ -31,6 +31,7 @@
 #include "llvm/Object/Archive.h"
 #include "llvm/Option/ArgList.h"
 #include "llvm/Option/Option.h"
+#include "llvm/Support/FileSystem.h"
 #include "llvm/Support/Host.h"
 #include "llvm/Support/MemoryBuffer.h"
 #include "llvm/Support/Path.h"
@@ -99,6 +100,33 @@
   return {};
 }
 
+static Optional<std::string> findFramework(StringRef name) {
+  llvm::SmallString<260> symlink;
+  llvm::SmallString<260> location;
+  // TODO: support .tbd files
+
+  StringRef suffix;
+  std::tie(name, suffix) = name.split(",");
+  for (StringRef dir : config->frameworkSearchPaths) {
+    symlink = dir;
+    path::append(symlink, name + ".framework", name);
+    // If the symlink fails to resolve, skip to the next search path.
+    // NOTE: we must resolve the symlink before trying the suffixes, because
+    // there are no symlinks for the suffixed paths.
+    if (fs::real_path(symlink, location))
+      continue;
+    if (!suffix.empty()) {
+      llvm::Twine suffixed = location + suffix;
+      if (fs::exists(suffixed))
+        return suffixed.str();
+      // Suffix lookup failed, fall through to the no-suffix case.
+    }
+    if (fs::exists(location))
+      return location.str().str();
+  }
+  return {};
+}
+
 static TargetInfo *createTargetInfo(opt::InputArgList &args) {
   StringRef arch = args.getLastArgValue(OPT_arch, "x86_64");
   config->arch = llvm::MachO::getArchitectureFromName(
@@ -394,6 +422,15 @@
       error("library not found for -l" + name);
       break;
     }
+    case OPT_framework: {
+      StringRef name = arg->getValue();
+      if (Optional<std::string> path = findFramework(name)) {
+        addFile(*path);
+        break;
+      }
+      error("framework not found for -framework " + name);
+      break;
+    }
     case OPT_platform_version:
       handlePlatformVersion(arg);
       break;


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D83925.278354.patch
Type: text/x-patch
Size: 3842 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20200716/59e46439/attachment.bin>


More information about the llvm-commits mailing list