Skip to content

Commit b7a90ef

Browse files
committedApr 4, 2017
[ELF] Fail the link early if the map file path is invalid
As with the changes made in r297645, we do not want a potentially long link to be run, if it will ultimately fail because the map file is not writable. This change reuses the same functionality as the output file path check. See https://reviews.llvm.org/D30449 for further justification and explanations. Reviewers: ruiu Differential Revision: https://reviews.llvm.org/D31603 llvm-svn: 299420
1 parent 74f823a commit b7a90ef

File tree

5 files changed

+24
-15
lines changed

5 files changed

+24
-15
lines changed
 

‎lld/ELF/Driver.cpp

+6-4
Original file line numberDiff line numberDiff line change
@@ -860,10 +860,12 @@ template <class ELFT> void LinkerDriver::link(opt::InputArgList &Args) {
860860
if (Config->OutputFile.empty())
861861
Config->OutputFile = "a.out";
862862

863-
// Fail early if the output file is not writable. If a user has a long link,
864-
// e.g. due to a large LTO link, they do not wish to run it and find that it
865-
// failed because there was a mistake in their command-line.
866-
if (!isFileWritable(Config->OutputFile))
863+
// Fail early if the output file or map file is not writable. If a user has a
864+
// long link, e.g. due to a large LTO link, they do not wish to run it and
865+
// find that it failed because there was a mistake in their command-line.
866+
if (!isFileWritable(Config->OutputFile, "output file"))
867+
return;
868+
if (!isFileWritable(Config->MapFile, "map file"))
867869
return;
868870

869871
// Use default entry point name if no name was given via the command

‎lld/ELF/Filesystem.cpp

+2-2
Original file line numberDiff line numberDiff line change
@@ -70,9 +70,9 @@ void elf::unlinkAsync(StringRef Path) {
7070
// FileOutputBuffer doesn't touch a desitnation file until commit()
7171
// is called. We use that class without calling commit() to predict
7272
// if the given file is writable.
73-
bool elf::isFileWritable(StringRef Path) {
73+
bool elf::isFileWritable(StringRef Path, StringRef Desc) {
7474
if (auto EC = FileOutputBuffer::create(Path, 1).getError()) {
75-
error("cannot open output file " + Path + ": " + EC.message());
75+
error("cannot open " + Desc + " " + Path + ": " + EC.message());
7676
return false;
7777
}
7878
return true;

‎lld/ELF/Filesystem.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
namespace lld {
1616
namespace elf {
1717
void unlinkAsync(StringRef Path);
18-
bool isFileWritable(StringRef Path);
18+
bool isFileWritable(StringRef Path, StringRef FileDescription);
1919
}
2020
}
2121

‎lld/test/ELF/early-exit-for-bad-paths.s

+14-7
Original file line numberDiff line numberDiff line change
@@ -2,25 +2,32 @@
22
# RUN: llvm-mc -filetype=obj -triple=x86_64-pc-linux %s -o %t.o
33

44
# RUN: not ld.lld %t.o -o does_not_exist/output 2>&1 | \
5-
# RUN: FileCheck %s -check-prefixes=NO-DIR,CHECK
5+
# RUN: FileCheck %s -check-prefixes=NO-DIR-OUTPUT,CHECK
66
# RUN: not ld.lld %t.o -o %s/dir_is_a_file 2>&1 | \
7-
# RUN: FileCheck %s -check-prefixes=DIR-IS-FILE,CHECK
7+
# RUN: FileCheck %s -check-prefixes=DIR-IS-OUTPUT,CHECK
88

99
# RUN: echo "OUTPUT(\"does_not_exist/output\")" > %t.script
1010
# RUN: not ld.lld %t.o %t.script 2>&1 | \
11-
# RUN: FileCheck %s -check-prefixes=NO-DIR,CHECK
11+
# RUN: FileCheck %s -check-prefixes=NO-DIR-OUTPUT,CHECK
1212
# RUN: echo "OUTPUT(\"%s/dir_is_a_file\")" > %t.script
1313
# RUN: not ld.lld %t.o %t.script 2>&1 | \
14-
# RUN: FileCheck %s -check-prefixes=DIR-IS-FILE,CHECK
14+
# RUN: FileCheck %s -check-prefixes=DIR-IS-OUTPUT,CHECK
1515

16-
# NO-DIR: error: cannot open output file does_not_exist/output:
17-
# DIR-IS-FILE: error: cannot open output file {{.*}}/dir_is_a_file:
16+
# RUN: not ld.lld %t.o -o %t -Map=does_not_exist/output 2>&1 | \
17+
# RUN: FileCheck %s -check-prefixes=NO-DIR-MAP,CHECK
18+
# RUN: not ld.lld %t.o -o %t -Map=%s/dir_is_a_file 2>&1 | \
19+
# RUN: FileCheck %s -check-prefixes=DIR-IS-MAP,CHECK
20+
21+
# NO-DIR-OUTPUT: error: cannot open output file does_not_exist/output:
22+
# DIR-IS-OUTPUT: error: cannot open output file {{.*}}/dir_is_a_file:
23+
# NO-DIR-MAP: error: cannot open map file does_not_exist/output:
24+
# DIR-IS-MAP: error: cannot open map file {{.*}}/dir_is_a_file:
1825

1926
# We should exit before doing the actual link. If an undefined symbol error is
2027
# discovered we haven't bailed out early as expected.
2128
# CHECK-NOT: undefined_symbol
2229

23-
# RUN: not ld.lld %t.o -o / 2>&1 | FileCheck %s -check-prefixes=ROOT
30+
# RUN: not ld.lld %t.o -o / 2>&1 | FileCheck %s -check-prefixes=ROOT,CHECK
2431
# ROOT: error: cannot open output file /
2532

2633
.globl _start

‎lld/test/ELF/map-file.s

+1-1
Original file line numberDiff line numberDiff line change
@@ -59,4 +59,4 @@ local:
5959

6060
// RUN: not ld.lld %t1.o %t2.o %t3.o %t4.a -o %t -Map=/ 2>&1 \
6161
// RUN: | FileCheck -check-prefix=FAIL %s
62-
// FAIL: cannot open /
62+
// FAIL: cannot open map file /

0 commit comments

Comments
 (0)
Please sign in to comment.