[lld] r238618 - COFF: Move machine type auto-detection to SymbolTable.
Peter Collingbourne
peter at pcc.me.uk
Fri May 29 14:47:36 PDT 2015
Author: pcc
Date: Fri May 29 16:47:36 2015
New Revision: 238618
URL: http://llvm.org/viewvc/llvm-project?rev=238618&view=rev
Log:
COFF: Move machine type auto-detection to SymbolTable.
The new mechanism is less code, and fixes the case where all inputs
are archives.
Differential Revision: http://reviews.llvm.org/D10136
Added:
lld/trunk/test/COFF/Inputs/ret42.lib
Modified:
lld/trunk/COFF/DriverUtils.cpp
lld/trunk/COFF/SymbolTable.h
lld/trunk/COFF/Writer.cpp
lld/trunk/test/COFF/machine.test
Modified: lld/trunk/COFF/DriverUtils.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/COFF/DriverUtils.cpp?rev=238618&r1=238617&r2=238618&view=diff
==============================================================================
--- lld/trunk/COFF/DriverUtils.cpp (original)
+++ lld/trunk/COFF/DriverUtils.cpp Fri May 29 16:47:36 2015
@@ -87,24 +87,6 @@ std::string findFile(StringRef Filename)
return Filename;
}
-// Peeks at the file header to get architecture (e.g. i386 or AMD64).
-// Returns "unknown" if it's not a valid object file.
-static MachineTypes getFileMachineType(StringRef Path) {
- file_magic Magic;
- if (identify_magic(Path, Magic))
- return IMAGE_FILE_MACHINE_UNKNOWN;
- if (Magic != file_magic::coff_object)
- return IMAGE_FILE_MACHINE_UNKNOWN;
- ErrorOr<std::unique_ptr<MemoryBuffer>> BufOrErr = MemoryBuffer::getFile(Path);
- if (BufOrErr.getError())
- return IMAGE_FILE_MACHINE_UNKNOWN;
- std::error_code EC;
- llvm::object::COFFObjectFile Obj(BufOrErr.get()->getMemBufferRef(), EC);
- if (EC)
- return IMAGE_FILE_MACHINE_UNKNOWN;
- return static_cast<MachineTypes>(Obj.getMachine());
-}
-
// Returns /machine's value.
ErrorOr<MachineTypes> getMachineType(llvm::opt::InputArgList *Args) {
if (auto *Arg = Args->getLastArg(OPT_machine)) {
@@ -118,13 +100,6 @@ ErrorOr<MachineTypes> getMachineType(llv
return make_dynamic_error_code("unknown /machine argument" + S);
return MT;
}
- // If /machine option is missing, we need to take a look at
- // the magic byte of the first object file to infer machine type.
- for (auto *Arg : Args->filtered(OPT_INPUT)) {
- MachineTypes MT = getFileMachineType(Arg->getValue());
- if (MT != IMAGE_FILE_MACHINE_UNKNOWN)
- return MT;
- }
return IMAGE_FILE_MACHINE_UNKNOWN;
}
Modified: lld/trunk/COFF/SymbolTable.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/COFF/SymbolTable.h?rev=238618&r1=238617&r2=238618&view=diff
==============================================================================
--- lld/trunk/COFF/SymbolTable.h (original)
+++ lld/trunk/COFF/SymbolTable.h Fri May 29 16:47:36 2015
@@ -53,6 +53,9 @@ public:
// order to create the import descriptor table.
std::vector<std::unique_ptr<ImportFile>> ImportFiles;
+ // The writer needs to infer the machine type from the object files.
+ std::vector<std::unique_ptr<ObjectFile>> ObjectFiles;
+
private:
std::error_code addObject(ObjectFile *File);
std::error_code addArchive(ArchiveFile *File);
@@ -63,7 +66,6 @@ private:
void addInitialSymbol(SymbolBody *Body);
std::unordered_map<StringRef, Symbol *> Symtab;
- std::vector<std::unique_ptr<ObjectFile>> ObjectFiles;
std::vector<std::unique_ptr<ArchiveFile>> ArchiveFiles;
std::vector<std::unique_ptr<SymbolBody>> OwnedSymbols;
llvm::BumpPtrAllocator Alloc;
Modified: lld/trunk/COFF/Writer.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/COFF/Writer.cpp?rev=238618&r1=238617&r2=238618&view=diff
==============================================================================
--- lld/trunk/COFF/Writer.cpp (original)
+++ lld/trunk/COFF/Writer.cpp Fri May 29 16:47:36 2015
@@ -227,6 +227,17 @@ void Writer::assignAddresses() {
RoundUpToAlignment(FileOff - SizeOfHeaders, FileAlignment);
}
+static MachineTypes
+inferMachineType(std::vector<std::unique_ptr<ObjectFile>> &ObjectFiles) {
+ for (std::unique_ptr<ObjectFile> &File : ObjectFiles) {
+ // Try to infer machine type from the magic byte of the object file.
+ auto MT = static_cast<MachineTypes>(File->getCOFFObj()->getMachine());
+ if (MT != IMAGE_FILE_MACHINE_UNKNOWN)
+ return MT;
+ }
+ return IMAGE_FILE_MACHINE_UNKNOWN;
+}
+
void Writer::writeHeader() {
// Write DOS stub
uint8_t *Buf = Buffer->getBufferStart();
@@ -241,10 +252,15 @@ void Writer::writeHeader() {
memcpy(Buf, PEMagic, sizeof(PEMagic));
Buf += sizeof(PEMagic);
+ // Determine machine type, infer if needed. TODO: diagnose conflicts.
+ MachineTypes MachineType = Config->MachineType;
+ if (MachineType == IMAGE_FILE_MACHINE_UNKNOWN)
+ MachineType = inferMachineType(Symtab->ObjectFiles);
+
// Write COFF header
auto *COFF = reinterpret_cast<coff_file_header *>(Buf);
Buf += sizeof(*COFF);
- COFF->Machine = Config->MachineType;
+ COFF->Machine = MachineType;
COFF->NumberOfSections = OutputSections.size();
COFF->Characteristics =
(IMAGE_FILE_EXECUTABLE_IMAGE | IMAGE_FILE_RELOCS_STRIPPED |
Added: lld/trunk/test/COFF/Inputs/ret42.lib
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/COFF/Inputs/ret42.lib?rev=238618&view=auto
==============================================================================
Binary files lld/trunk/test/COFF/Inputs/ret42.lib (added) and lld/trunk/test/COFF/Inputs/ret42.lib Fri May 29 16:47:36 2015 differ
Modified: lld/trunk/test/COFF/machine.test
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/COFF/machine.test?rev=238618&r1=238617&r2=238618&view=diff
==============================================================================
--- lld/trunk/test/COFF/machine.test (original)
+++ lld/trunk/test/COFF/machine.test Fri May 29 16:47:36 2015
@@ -1,6 +1,15 @@
# RUN: lld -flavor link2 /entry:main /machine:x64 /out:%t.exe \
# RUN: %p/Inputs/ret42.obj
# RUN: llvm-readobj -file-headers %t.exe | FileCheck -check-prefix=AMD64 %s
+# RUN: lld -flavor link2 /entry:main /machine:x64 /out:%t.exe \
+# RUN: %p/Inputs/ret42.lib
+# RUN: llvm-readobj -file-headers %t.exe | FileCheck -check-prefix=AMD64 %s
+# RUN: lld -flavor link2 /entry:main /out:%t.exe \
+# RUN: %p/Inputs/ret42.obj
+# RUN: llvm-readobj -file-headers %t.exe | FileCheck -check-prefix=AMD64 %s
+# RUN: lld -flavor link2 /entry:main /out:%t.exe \
+# RUN: %p/Inputs/ret42.lib
+# RUN: llvm-readobj -file-headers %t.exe | FileCheck -check-prefix=AMD64 %s
AMD64: Machine: IMAGE_FILE_MACHINE_AMD64
More information about the llvm-commits
mailing list