[lld] r291413 - Add linker-script-included files to reproduce tar files.

Rui Ueyama via llvm-commits llvm-commits at lists.llvm.org
Sun Jan 8 17:42:03 PST 2017


Author: ruiu
Date: Sun Jan  8 19:42:02 2017
New Revision: 291413

URL: http://llvm.org/viewvc/llvm-project?rev=291413&view=rev
Log:
Add linker-script-included files to reproduce tar files.

Previously, files added using INCLUDE directive weren't added
to reproduce archives. In this patch, I defined a function to
open a file and use that from Driver and LinkerScript.

Modified:
    lld/trunk/ELF/Driver.cpp
    lld/trunk/ELF/Driver.h
    lld/trunk/ELF/InputFiles.cpp
    lld/trunk/ELF/InputFiles.h
    lld/trunk/ELF/LinkerScript.cpp
    lld/trunk/test/ELF/reproduce-linkerscript.s

Modified: lld/trunk/ELF/Driver.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Driver.cpp?rev=291413&r1=291412&r2=291413&view=diff
==============================================================================
--- lld/trunk/ELF/Driver.cpp (original)
+++ lld/trunk/ELF/Driver.cpp Sun Jan  8 19:42:02 2017
@@ -26,6 +26,7 @@
 #include "llvm/ADT/StringSwitch.h"
 #include "llvm/Support/CommandLine.h"
 #include "llvm/Support/Path.h"
+#include "llvm/Support/TarWriter.h"
 #include "llvm/Support/TargetSelect.h"
 #include "llvm/Support/raw_ostream.h"
 #include <cstdlib>
@@ -51,6 +52,7 @@ bool elf::link(ArrayRef<const char *> Ar
   ErrorCount = 0;
   ErrorOS = &Error;
   Argv0 = Args[0];
+  Tar = nullptr;
 
   Config = make<Configuration>();
   Driver = make<LinkerDriver>();
@@ -170,25 +172,6 @@ void LinkerDriver::addFile(StringRef Pat
   }
 }
 
-Optional<MemoryBufferRef> LinkerDriver::readFile(StringRef Path) {
-  if (Config->Verbose)
-    outs() << Path << "\n";
-
-  auto MBOrErr = MemoryBuffer::getFile(Path);
-  if (auto EC = MBOrErr.getError()) {
-    error(EC, "cannot open " + Path);
-    return None;
-  }
-  std::unique_ptr<MemoryBuffer> &MB = *MBOrErr;
-  MemoryBufferRef MBRef = MB->getMemBufferRef();
-  make<std::unique_ptr<MemoryBuffer>>(std::move(MB)); // take MB ownership
-
-  if (Tar)
-    Tar->append(relativeToRoot(Path), MBRef.getBuffer());
-
-  return MBRef;
-}
-
 // Add a given library by searching it from input search paths.
 void LinkerDriver::addLibrary(StringRef Name) {
   if (Optional<std::string> Path = searchLibrary(Name))
@@ -313,9 +296,10 @@ void LinkerDriver::main(ArrayRef<const c
     Expected<std::unique_ptr<TarWriter>> ErrOrWriter =
         TarWriter::create(Path, path::stem(Path));
     if (ErrOrWriter) {
-      Tar = std::move(*ErrOrWriter);
+      Tar = ErrOrWriter->get();
       Tar->append("response.txt", createResponseFile(Args));
       Tar->append("version.txt", getLLDVersion() + "\n");
+      make<std::unique_ptr<TarWriter>>(std::move(*ErrOrWriter));
     } else {
       error(Twine("--reproduce: failed to open ") + Path + ": " +
             toString(ErrOrWriter.takeError()));

Modified: lld/trunk/ELF/Driver.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Driver.h?rev=291413&r1=291412&r2=291413&view=diff
==============================================================================
--- lld/trunk/ELF/Driver.h (original)
+++ lld/trunk/ELF/Driver.h Sun Jan  8 19:42:02 2017
@@ -17,7 +17,6 @@
 #include "llvm/ADT/StringRef.h"
 #include "llvm/ADT/StringSet.h"
 #include "llvm/Option/ArgList.h"
-#include "llvm/Support/TarWriter.h"
 #include "llvm/Support/raw_ostream.h"
 
 namespace lld {
@@ -30,11 +29,9 @@ public:
   void main(ArrayRef<const char *> Args, bool CanExitEarly);
   void addFile(StringRef Path);
   void addLibrary(StringRef Name);
-  std::unique_ptr<llvm::TarWriter> Tar; // for reproduce
 
 private:
   std::vector<MemoryBufferRef> getArchiveMembers(MemoryBufferRef MB);
-  llvm::Optional<MemoryBufferRef> readFile(StringRef Path);
   void readConfigs(llvm::opt::InputArgList &Args);
   void createFiles(llvm::opt::InputArgList &Args);
   void inferMachineType();

Modified: lld/trunk/ELF/InputFiles.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/InputFiles.cpp?rev=291413&r1=291412&r2=291413&view=diff
==============================================================================
--- lld/trunk/ELF/InputFiles.cpp (original)
+++ lld/trunk/ELF/InputFiles.cpp Sun Jan  8 19:42:02 2017
@@ -8,7 +8,6 @@
 //===----------------------------------------------------------------------===//
 
 #include "InputFiles.h"
-#include "Driver.h"
 #include "Error.h"
 #include "InputSection.h"
 #include "LinkerScript.h"
@@ -26,6 +25,7 @@
 #include "llvm/MC/StringTableBuilder.h"
 #include "llvm/Object/ELFObjectFile.h"
 #include "llvm/Support/Path.h"
+#include "llvm/Support/TarWriter.h"
 #include "llvm/Support/raw_ostream.h"
 
 using namespace llvm;
@@ -36,6 +36,8 @@ using namespace llvm::sys::fs;
 using namespace lld;
 using namespace lld::elf;
 
+TarWriter *elf::Tar;
+
 namespace {
 // In ELF object file all section addresses are zero. If we have multiple
 // .text sections (when using -ffunction-section or comdat group) then
@@ -53,6 +55,24 @@ public:
 };
 }
 
+Optional<MemoryBufferRef> elf::readFile(StringRef Path) {
+  if (Config->Verbose)
+    outs() << Path << "\n";
+
+  auto MBOrErr = MemoryBuffer::getFile(Path);
+  if (auto EC = MBOrErr.getError()) {
+    error(EC, "cannot open " + Path);
+    return None;
+  }
+  std::unique_ptr<MemoryBuffer> &MB = *MBOrErr;
+  MemoryBufferRef MBRef = MB->getMemBufferRef();
+  make<std::unique_ptr<MemoryBuffer>>(std::move(MB)); // take MB ownership
+
+  if (Tar)
+    Tar->append(relativeToRoot(Path), MBRef.getBuffer());
+  return MBRef;
+}
+
 template <class ELFT> void elf::ObjectFile<ELFT>::initializeDwarfLine() {
   std::unique_ptr<object::ObjectFile> Obj =
       check(object::ObjectFile::createObjectFile(this->MB),
@@ -524,9 +544,8 @@ ArchiveFile::getMember(const Archive::Sy
             "could not get the buffer for the member defining symbol " +
                 Sym->getName());
 
-  if (C.getParent()->isThin() && Driver->Tar)
-    Driver->Tar->append(relativeToRoot(check(C.getFullName())),
-                        Ret.getBuffer());
+  if (C.getParent()->isThin() && Tar)
+    Tar->append(relativeToRoot(check(C.getFullName())), Ret.getBuffer());
   if (C.getParent()->isThin())
     return {Ret, 0};
   return {Ret, C.getChildOffset()};

Modified: lld/trunk/ELF/InputFiles.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/InputFiles.h?rev=291413&r1=291412&r2=291413&view=diff
==============================================================================
--- lld/trunk/ELF/InputFiles.h (original)
+++ lld/trunk/ELF/InputFiles.h Sun Jan  8 19:42:02 2017
@@ -29,6 +29,7 @@
 
 namespace llvm {
 class DWARFDebugLine;
+class TarWriter;
 namespace lto {
 class InputFile;
 }
@@ -49,6 +50,13 @@ using llvm::object::Archive;
 class Lazy;
 class SymbolBody;
 
+// If -reproduce option is given, all input files are written
+// to this tar archive.
+extern llvm::TarWriter *Tar;
+
+// Opens a given file.
+llvm::Optional<MemoryBufferRef> readFile(StringRef Path);
+
 // The root class of input files.
 class InputFile {
 public:

Modified: lld/trunk/ELF/LinkerScript.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/LinkerScript.cpp?rev=291413&r1=291412&r2=291413&view=diff
==============================================================================
--- lld/trunk/ELF/LinkerScript.cpp (original)
+++ lld/trunk/ELF/LinkerScript.cpp Sun Jan  8 19:42:02 2017
@@ -1143,20 +1143,21 @@ void ScriptParser::readGroup() {
 
 void ScriptParser::readInclude() {
   StringRef Tok = unquote(next());
+
   // https://sourceware.org/binutils/docs/ld/File-Commands.html:
   // The file will be searched for in the current directory, and in any
   // directory specified with the -L option.
-  auto MBOrErr = MemoryBuffer::getFile(Tok);
-  if (!MBOrErr)
-    if (Optional<std::string> Path = findFromSearchPaths(Tok))
-      MBOrErr = MemoryBuffer::getFile(*Path);
-  if (!MBOrErr) {
-    setError("cannot open " + Tok);
+  if (sys::fs::exists(Tok)) {
+    if (Optional<MemoryBufferRef> MB = readFile(Tok))
+      tokenize(*MB);
+    return;
+  }
+  if (Optional<std::string> Path = findFromSearchPaths(Tok)) {
+    if (Optional<MemoryBufferRef> MB = readFile(*Path))
+      tokenize(*MB);
     return;
   }
-  MemoryBufferRef MBRef = (*MBOrErr)->getMemBufferRef();
-  make<std::unique_ptr<MemoryBuffer>>(std::move(*MBOrErr)); // take MB ownership
-  tokenize(MBRef);
+  setError("cannot open " + Tok);
 }
 
 void ScriptParser::readOutput() {

Modified: lld/trunk/test/ELF/reproduce-linkerscript.s
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/ELF/reproduce-linkerscript.s?rev=291413&r1=291412&r2=291413&view=diff
==============================================================================
--- lld/trunk/test/ELF/reproduce-linkerscript.s (original)
+++ lld/trunk/test/ELF/reproduce-linkerscript.s Sun Jan  8 19:42:02 2017
@@ -4,10 +4,13 @@
 # RUN: mkdir -p %t.dir/build
 # RUN: llvm-mc -filetype=obj -triple=x86_64-unknown-linux %s -o %t.dir/build/foo.o
 # RUN: echo "INPUT(\"%t.dir/build/foo.o\")" > %t.dir/build/foo.script
+# RUN: echo "INCLUDE \"%t.dir/build/bar.script\"" >> %t.dir/build/foo.script
+# RUN: echo "/* empty */" > %t.dir/build/bar.script
 # RUN: cd %t.dir
 # RUN: ld.lld build/foo.script -o bar --reproduce repro.tar
 # RUN: tar xf repro.tar
 # RUN: diff build/foo.script repro/%:t.dir/build/foo.script
+# RUN: diff build/bar.script repro/%:t.dir/build/bar.script
 # RUN: diff build/foo.o repro/%:t.dir/build/foo.o
 
 .globl _start




More information about the llvm-commits mailing list