[lld-macho] Support lookup of dylibs in frameworks

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

Reviewed By: #lld-macho, compnerd

Differential Revision: https://reviews.llvm.org/D83925
This commit is contained in:
Jez Ng 2020-07-26 12:46:46 -07:00
parent df12524e6b
commit 9282d04e04
3 changed files with 67 additions and 1 deletions

View File

@ -30,7 +30,6 @@ struct Configuration {
llvm::MachO::Architecture arch;
llvm::MachO::HeaderFileType outputType;
std::vector<llvm::StringRef> librarySearchPaths;
// TODO: use the framework search paths
std::vector<llvm::StringRef> frameworkSearchPaths;
llvm::DenseMap<llvm::StringRef, SymbolPriorityEntry> priorities;
};

View File

@ -30,6 +30,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"
@ -98,6 +99,32 @@ static Optional<std::string> findLibrary(StringRef name) {
return {};
}
static Optional<std::string> findFramework(StringRef name) {
// TODO: support .tbd files
llvm::SmallString<260> symlink;
llvm::SmallString<260> location;
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(
@ -393,13 +420,24 @@ bool macho::link(llvm::ArrayRef<const char *> argsArr, bool canExitEarly,
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;
case OPT_o:
case OPT_dylib:
case OPT_e:
case OPT_F:
case OPT_L:
case OPT_install_name:
case OPT_Z:
case OPT_arch:
// handled elsewhere

View File

@ -0,0 +1,29 @@
# REQUIRES: x86, shell
# 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