Index: ELF/ScriptParser.cpp =================================================================== --- ELF/ScriptParser.cpp +++ ELF/ScriptParser.cpp @@ -86,7 +86,7 @@ unsigned readPhdrType(); SortSectionPolicy readSortKind(); SymbolAssignment *readProvideHidden(bool Provide, bool Hidden); - SymbolAssignment *readProvideOrAssignment(StringRef Tok); + SymbolAssignment *readProvideOrAssignment(StringRef Tok, bool Global); void readSort(); AssertCommand *readAssert(); Expr readAssertExpr(); @@ -242,7 +242,7 @@ readSections(); } else if (Tok == "VERSION") { readVersion(); - } else if (SymbolAssignment *Cmd = readProvideOrAssignment(Tok)) { + } else if (SymbolAssignment *Cmd = readProvideOrAssignment(Tok, true)) { Script->Opt.Commands.push_back(Cmd); } else { setError("unknown directive: " + Tok); @@ -405,7 +405,7 @@ expect("{"); while (!ErrorCount && !consume("}")) { StringRef Tok = next(); - BaseCommand *Cmd = readProvideOrAssignment(Tok); + BaseCommand *Cmd = readProvideOrAssignment(Tok, true); if (!Cmd) { if (Tok == "ASSERT") Cmd = readAssert(); @@ -629,7 +629,7 @@ StringRef Tok = next(); if (Tok == ";") { // Empty commands are allowed. Do nothing here. - } else if (SymbolAssignment *Assign = readProvideOrAssignment(Tok)) { + } else if (SymbolAssignment *Assign = readProvideOrAssignment(Tok, false)) { Cmd->Commands.push_back(Assign); } else if (BytesDataCommand *Data = readBytesDataCommand(Tok)) { Cmd->Commands.push_back(Data); @@ -696,12 +696,18 @@ return Cmd; } -SymbolAssignment *ScriptParser::readProvideOrAssignment(StringRef Tok) { +SymbolAssignment *ScriptParser::readProvideOrAssignment(StringRef Tok, + bool Global) { SymbolAssignment *Cmd = nullptr; if (peek() == "=" || peek() == "+=") { Cmd = readAssignment(Tok); expect(";"); - } else if (Tok == "PROVIDE") { + if (Global && Tok != ".") + Script->Opt.ReferencedSymbols.push_back(Tok); + return Cmd; + } + + if (Tok == "PROVIDE") { Cmd = readProvideHidden(true, false); } else if (Tok == "HIDDEN") { Cmd = readProvideHidden(false, true); Index: test/ELF/linkerscript/align.s =================================================================== --- test/ELF/linkerscript/align.s +++ test/ELF/linkerscript/align.s @@ -61,8 +61,8 @@ # SYMBOLS-LABEL: SYMBOL TABLE: # SYMBOLS-NEXT: 0000000000000000 *UND* 00000000 # SYMBOLS-NEXT: 0000000000014008 .text 00000000 _start -# SYMBOLS-NEXT: 0000000000010000 *ABS* 00000000 __code_base__ # SYMBOLS-NEXT: 0000000000001000 *ABS* 00000000 VAR +# SYMBOLS-NEXT: 0000000000010000 *ABS* 00000000 __code_base__ # SYMBOLS-NEXT: 0000000000011000 .bbb 00000000 __start_bbb # SYMBOLS-NEXT: 0000000000012000 .bbb 00000000 __end_bbb Index: test/ELF/linkerscript/symbols-synthetic.s =================================================================== --- test/ELF/linkerscript/symbols-synthetic.s +++ test/ELF/linkerscript/symbols-synthetic.s @@ -61,6 +61,7 @@ # SIMPLE-NEXT: 0000000000000120 .foo 00000000 _begin_sec # SIMPLE-NEXT: 0000000000000128 *ABS* 00000000 _end_sec_abs # SIMPLE-NEXT: 0000000000001048 .text 00000000 _start +# SIMPLE-NEXT: 0000000000000ee4 *ABS* 00000000 size_foo_3 # SIMPLE-NEXT: 0000000000000120 .foo 00000000 begin_foo # SIMPLE-NEXT: 0000000000000128 .foo 00000000 end_foo # SIMPLE-NEXT: 0000000000000008 *ABS* 00000000 size_foo_1 @@ -68,7 +69,6 @@ # SIMPLE-NEXT: 0000000000001000 .foo 00000000 begin_bar # SIMPLE-NEXT: 0000000000001004 .foo 00000000 end_bar # SIMPLE-NEXT: 0000000000000ee4 *ABS* 00000000 size_foo_2 -# SIMPLE-NEXT: 0000000000000ee4 *ABS* 00000000 size_foo_3 # SIMPLE-NEXT: 0000000000001004 .eh_frame_hdr 00000000 __eh_frame_hdr_start # SIMPLE-NEXT: 0000000000001010 *ABS* 00000000 __eh_frame_hdr_start2 # SIMPLE-NEXT: 0000000000001018 .eh_frame_hdr 00000000 __eh_frame_hdr_end Index: test/ELF/lto/linker-script-symbols2.ll =================================================================== --- test/ELF/lto/linker-script-symbols2.ll +++ test/ELF/lto/linker-script-symbols2.ll @@ -0,0 +1,48 @@ +; REQUIRES: x86 +; RUN: llvm-as %s -o %t.o + +; RUN: echo "foo = 1;" > %t.script +; RUN: ld.lld -m elf_x86_64 %t.o -o %t2 --script %t.script -save-temps +; RUN: llvm-readobj -symbols %t2.lto.o | FileCheck %s + +; CHECK-NOT: bar +; CHECK: Symbol { +; CHECK: Name: foo +; CHECK-NEXT: Value: 0x0 +; CHECK-NEXT: Size: 4 +; CHECK-NEXT: Binding: Global +; CHECK-NEXT: Type: Object +; CHECK-NEXT: Other: 0 +; CHECK-NEXT: Section: .bss.foo +; CHECK-NEXT: } +; CHECK-NEXT:] + +; RUN: llvm-readobj -symbols %t2 | FileCheck %s --check-prefix=VAL +; VAL: Symbol { +; VAL: Name: foo +; VAL-NEXT: Value: 0x1 +; VAL-NEXT: Size: +; VAL-NEXT: Binding: Global +; VAL-NEXT: Type: None +; VAL-NEXT: Other: +; VAL-NEXT: Section: Absolute +; VAL-NEXT: } + +; RUN: echo "zed = 1;" > %t2.script +; RUN: ld.lld -m elf_x86_64 %t.o -o %t3 --script %t2.script +; RUN: llvm-readobj -symbols %t3 | FileCheck %s --check-prefix=ABS +; ABS: Symbol { +; ABS: Name: zed +; ABS-NEXT: Value: 0x1 +; ABS-NEXT: Size: 0 +; ABS-NEXT: Binding: Global +; ABS-NEXT: Type: None +; ABS-NEXT: Other: 0 +; ABS-NEXT: Section: Absolute +; ABS-NEXT: } + +target triple = "x86_64-unknown-linux-gnu" +target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128" + +@foo = global i32 0 +@bar = global i32 0