diff --git a/lld/MachO/Driver.cpp b/lld/MachO/Driver.cpp --- a/lld/MachO/Driver.cpp +++ b/lld/MachO/Driver.cpp @@ -73,21 +73,18 @@ return args; } -// This is for -lfoo. We'll look for libfoo.dylib from search paths. -static Optional findDylib(StringRef name) { - for (StringRef dir : config->searchPaths) { - std::string path = (dir + "/lib" + name + ".dylib").str(); - if (fs::exists(path)) - return path; - } - return None; -} +static Optional findLibrary(StringRef name) { + std::string shared = (llvm::Twine("lib") + name + ".dylib").str(); + std::string archive = (llvm::Twine("lib") + name + ".a").str(); + llvm::SmallString<260> location; -static Optional findArchive(StringRef name) { for (StringRef dir : config->searchPaths) { - std::string path = (dir + "/lib" + name + ".a").str(); - if (fs::exists(path)) - return path; + for (StringRef library : {shared, archive}) { + location = dir; + llvm::sys::path::append(location, library); + if (fs::exists(location)) + return location.str().str(); + } } return None; } @@ -296,12 +293,11 @@ break; case OPT_l: { StringRef name = arg->getValue(); - if (Optional path = findDylib(name)) + if (Optional path = findLibrary(name)) { addFile(*path); - else if (Optional path = findArchive(name)) - addFile(*path); - else - error("library not found for -l" + name); + break; + } + error("library not found for -l" + name); break; } case OPT_platform_version: { diff --git a/lld/test/MachO/link-search-order.s b/lld/test/MachO/link-search-order.s new file mode 100644 --- /dev/null +++ b/lld/test/MachO/link-search-order.s @@ -0,0 +1,43 @@ +# REQUIRES: x86 + +# RUN: mkdir -p %t +# +# RUN: llvm-mc -filetype obj -triple x86_64-apple-darwin %p/Inputs/libhello.s -o %t/hello.o +# RUN: lld -flavor darwinnew -dylib -install_name @executable_path/libhello.dylib %t/hello.o -o %t/libhello.dylib +# +# RUN: llvm-mc -filetype obj -triple x86_64-apple-darwin %p/Inputs/libgoodbye.s -o %t/goodbye.o +# RUN: lld -flavor darwinnew -dylib -install_name @executable_path/libgoodbye.dylib %t/goodbye.o -o %t/libgoodbye.dylib +# RUN: llvm-ar --format=darwin crs %t/libgoodbye.a %t/goodbye.o +# +# RUN: llvm-mc -filetype obj -triple x86_64-apple-darwin %s -o %t/test.o +# RUN: lld -flavor darwinnew -o %t/test -Z -L%t -lhello -lgoodbye %t/test.o +# +# RUN: llvm-objdump --macho --dylibs-used %t/test | FileCheck %s + +# CHECK: @executable_path/libhello.dylib +# CHECK: @executable_path/libgoodbye.dylib +# CHECK: /usr/lib/libSystem.B.dylib + +.section __TEXT,__text +.global _main + +_main: + movl $0x2000004, %eax # write() + mov $1, %rdi # stdout + movq _hello_world@GOTPCREL(%rip), %rsi + mov $13, %rdx # length + syscall + + movl $0x2000004, %eax # write() + mov $1, %rdi # stdout + movq _hello_its_me@GOTPCREL(%rip), %rsi + mov $15, %rdx # length + syscall + + movl $0x2000004, %eax # write() + mov $1, %rdi # stdout + movq _goodbye_world@GOTPCREL(%rip), %rsi + mov $15, %rdx # length + syscall + mov $0, %rax + ret