[PATCH] D44336: Implement --cref.
Rafael Ávila de Espíndola via Phabricator via llvm-commits
llvm-commits at lists.llvm.org
Wed Mar 14 13:26:58 PDT 2018
rafael added a comment.
LGTM
Rui Ueyama via Phabricator <reviews at reviews.llvm.org> writes:
> ruiu updated this revision to Diff 138440.
> ruiu added a comment.
>
> - address review comments.
>
> https://reviews.llvm.org/D44336
>
> Files:
>
> lld/ELF/Config.h
> lld/ELF/Driver.cpp
> lld/ELF/MapFile.cpp
> lld/ELF/MapFile.h
> lld/ELF/Options.td
> lld/ELF/Writer.cpp
> lld/test/ELF/cref.s
> lld/test/ELF/silent-ignore.test
>
> Index: lld/test/ELF/silent-ignore.test
> ===================================================================
>
> - lld/test/ELF/silent-ignore.test +++ lld/test/ELF/silent-ignore.test @@ -1,6 +1,5 @@ RUN: ld.lld --version \ RUN: -allow-shlib-undefined \ -RUN: -cref \ RUN: -g \ RUN: -no-add-needed \ RUN: -no-allow-shlib-undefined \ Index: lld/test/ELF/cref.s ===================================================================
> - /dev/null +++ lld/test/ELF/cref.s @@ -0,0 +1,26 @@ +// REQUIRES: x86 + +// RUN: echo '.global foo; foo:' | llvm-mc -filetype=obj -triple=x86_64-pc-linux - -o %t1.o +// RUN: echo '.global foo, bar; bar:' | llvm-mc -filetype=obj -triple=x86_64-pc-linux - -o %t2.o +// RUN: llvm-mc -filetype=obj -triple=x86_64-pc-linux %s -o %t3.o +// RUN: ld.lld -shared -o %t1.so %t1.o -gc-sections +// RUN: ld.lld -o /dev/null %t1.so %t2.o %t3.o -cref | FileCheck -strict-whitespace %s + +// CHECK: Symbol File +// CHECK-NEXT: bar {{.*}}2.o +// CHECK-NEXT: {{.*}}3.o +// CHECK-NEXT: foo {{.*}}1.so +// CHECK-NEXT: {{.*}}2.o +// CHECK-NEXT: {{.*}}3.o +// CHECK-NEXT: _start {{.*}}3.o +// CHECK-NEXT: baz {{.*}}3.o + +.global _start, foo, bar, baz +_start: + call foo + call bar +localsym: +baz: + +.section .text.a,"ax", at progbits +discarded: Index: lld/ELF/Writer.cpp ===================================================================
> - lld/ELF/Writer.cpp +++ lld/ELF/Writer.cpp @@ -475,8 +475,9 @@ if (errorCount()) return;
> - // Handle -Map option. + // Handle -Map and -cref options. writeMapFile(); + writeCrossReferenceTable(); if (errorCount()) return;
>
> Index: lld/ELF/Options.td ===================================================================
> - lld/ELF/Options.td +++ lld/ELF/Options.td @@ -75,6 +75,10 @@ def color_diagnostics_eq: J<"color-diagnostics=">, HelpText<"Use colors in diagnostics">;
>
> +defm cref: B<"cref", + "Output cross reference table", + "Do not output cross reference table">; + defm define_common: B<"define-common", "Assign space to common symbols", "Do not assign space to common symbols">; @@ -420,7 +424,6 @@
>
> // Options listed below are silently ignored for now for compatibility. def allow_shlib_undefined: F<"allow-shlib-undefined">; -def cref: F<"cref">; def detect_odr_violations: F<"detect-odr-violations">; def g: Flag<["-"], "g">; def long_plt: F<"long-plt">; Index: lld/ELF/MapFile.h ===================================================================
> - lld/ELF/MapFile.h +++ lld/ELF/MapFile.h @@ -13,6 +13,7 @@ namespace lld { namespace elf { void writeMapFile(); +void writeCrossReferenceTable(); } // namespace elf } // namespace lld
>
> Index: lld/ELF/MapFile.cpp ===================================================================
> - lld/ELF/MapFile.cpp +++ lld/ELF/MapFile.cpp @@ -28,6 +28,8 @@ #include "SyntheticSections.h" #include "lld/Common/Strings.h" #include "lld/Common/Threads.h" +#include "llvm/ADT/MapVector.h" +#include "llvm/ADT/SetVector.h" #include "llvm/Support/raw_ostream.h"
>
> using namespace llvm; @@ -146,3 +148,50 @@ } } } + +static void print(StringRef A, StringRef B) { + outs() << left_justify(A, 49) << " " << B << "\n"; +} + +// Output a cross reference table to stdout. This is for --cref. +// +// For each global symbol, we print out a file that defines the symbol +// followed by files that uses that symbol. Here is an example. +// +// strlen /lib/x86_64-linux-gnu/libc.so.6 +// tools/lld/tools/lld/CMakeFiles/lld.dir/lld.cpp.o +// lib/libLLVMSupport.a(PrettyStackTrace.cpp.o) +// +// In this case, strlen is defined by libc.so.6 and used by other two +// files. +void elf::writeCrossReferenceTable() { + if (!Config->Cref) + return; + + // Collect symbols and files. + MapVector<Symbol *, SetVector<InputFile *>> Map; + for (InputFile *File : ObjectFiles) { + for (Symbol *Sym : File->getSymbols()) { + if (isa<SharedSymbol>(Sym)) + Map[Sym].insert(File); + if (auto *D = dyn_cast<Defined>(Sym)) + if (!D->isLocal() && (!D->Section || D->Section->Live)) + Map[D].insert(File); + } + } + + // Print out a header. + outs() << "Cross Reference Table\n\n"; + print("Symbol", "File"); + + // Print out a table. + for (auto KV : Map) { + Symbol *Sym = KV.first; + SetVector<InputFile *> &Files = KV.second; + + print(toString(*Sym), toString(Sym->File)); + for (InputFile *File : Files) + if (File != Sym->File) + print("", toString(File)); + } +} Index: lld/ELF/Driver.cpp ===================================================================
> - lld/ELF/Driver.cpp +++ lld/ELF/Driver.cpp @@ -618,6 +618,7 @@ Args.hasFlag(OPT_check_sections, OPT_no_check_sections, true); Config->Chroot = Args.getLastArgValue(OPT_chroot); Config->CompressDebugSections = getCompressDebugSections(Args); + Config->Cref = Args.hasFlag(OPT_cref, OPT_no_cref, false); Config->DefineCommon = Args.hasFlag(OPT_define_common, OPT_no_define_common, !Args.hasArg(OPT_relocatable)); Config->Demangle = Args.hasFlag(OPT_demangle, OPT_no_demangle, true); Index: lld/ELF/Config.h ===================================================================
> - lld/ELF/Config.h +++ lld/ELF/Config.h @@ -113,6 +113,7 @@ bool BsymbolicFunctions; bool CheckSections; bool CompressDebugSections; + bool Cref; bool DefineCommon; bool Demangle = true; bool DisableVerify;
https://reviews.llvm.org/D44336
More information about the llvm-commits
mailing list