[PECOFF] Emit PE+ idata tables.

Import tables in the PE+ format is an array of 64 bit numbers,
although the executable size is still limited to 4GB in PE+.

llvm-svn: 216039
This commit is contained in:
Rui Ueyama
2014-08-20 01:09:42 +00:00
parent 19c2e2fab2
commit a0b988cb63
4 changed files with 40 additions and 35 deletions

View File

@@ -50,9 +50,16 @@ std::vector<uint8_t> HintNameAtom::assembleRawContent(uint16_t hint,
}
std::vector<uint8_t>
ImportTableEntryAtom::assembleRawContent(uint32_t contents) {
ImportTableEntryAtom::assembleRawContent(uint32_t rva, bool is64) {
// The element size of the import table is 32 bit in PE and 64 bit
// in PE+. In PE+, bits 62-31 are filled with zero.
if (is64) {
std::vector<uint8_t> ret(8);
*reinterpret_cast<llvm::support::ulittle64_t *>(&ret[0]) = rva;
return ret;
}
std::vector<uint8_t> ret(4);
*reinterpret_cast<llvm::support::ulittle32_t *>(&ret[0]) = contents;
*reinterpret_cast<llvm::support::ulittle32_t *>(&ret[0]) = rva;
return ret;
}
@@ -114,7 +121,7 @@ void IdataPass::perform(std::unique_ptr<MutableFile> &file) {
if (file->sharedLibrary().empty())
return;
idata::Context context(*file, _dummyFile);
idata::Context context(*file, _dummyFile, _is64);
std::map<StringRef, std::vector<COFFSharedLibraryAtom *> > sharedAtoms =
groupByLoadName(*file);
for (auto i : sharedAtoms) {

View File

@@ -24,6 +24,7 @@
#include "lld/Core/File.h"
#include "lld/Core/Pass.h"
#include "lld/Core/Simple.h"
#include "lld/ReaderWriter/PECOFFLinkingContext.h"
#include "llvm/Support/COFF.h"
#include <algorithm>
@@ -41,9 +42,11 @@ class ImportTableEntryAtom;
// A state object of this pass.
struct Context {
Context(MutableFile &f, VirtualFile &g) : file(f), dummyFile(g) {}
Context(MutableFile &f, VirtualFile &g, bool peplus)
: file(f), dummyFile(g), is64(peplus) {}
MutableFile &file;
VirtualFile &dummyFile;
bool is64;
};
/// The root class of all idata atoms.
@@ -79,9 +82,8 @@ private:
class ImportTableEntryAtom : public IdataAtom {
public:
ImportTableEntryAtom(Context &context, uint32_t contents,
StringRef sectionName)
: IdataAtom(context, assembleRawContent(contents)),
ImportTableEntryAtom(Context &ctx, uint32_t contents, StringRef sectionName)
: IdataAtom(ctx, assembleRawContent(contents, ctx.is64)),
_sectionName(sectionName) {}
StringRef customSectionName() const override {
@@ -89,7 +91,7 @@ public:
};
private:
std::vector<uint8_t> assembleRawContent(uint32_t contents);
std::vector<uint8_t> assembleRawContent(uint32_t contents, bool is64);
StringRef _sectionName;
};
@@ -131,7 +133,8 @@ public:
class IdataPass : public lld::Pass {
public:
IdataPass(const LinkingContext &ctx) : _dummyFile(ctx) {}
IdataPass(const PECOFFLinkingContext &ctx)
: _dummyFile(ctx), _is64(ctx.is64Bit()) {}
void perform(std::unique_ptr<MutableFile> &file) override;
@@ -146,6 +149,7 @@ private:
// read from a file, so we use this object.
VirtualFile _dummyFile;
bool _is64;
llvm::BumpPtrAllocator _alloc;
};

View File

@@ -6,15 +6,15 @@ sections:
- Name: .text
Characteristics: [ IMAGE_SCN_CNT_CODE, IMAGE_SCN_MEM_EXECUTE, IMAGE_SCN_MEM_READ ]
Alignment: 16
SectionData: C3
SectionData: C3C3C3C3
Relocations:
- VirtualAddress: 0
SymbolName: __imp__fn
Type: IMAGE_REL_AMD64_REL32
- Name: .data
Characteristics: [ IMAGE_SCN_CNT_INITIALIZED_DATA, IMAGE_SCN_MEM_READ, IMAGE_SCN_MEM_WRITE ]
Alignment: 16
SectionData: ''
- Name: '.debug$S'
Characteristics: [ IMAGE_SCN_CNT_INITIALIZED_DATA, IMAGE_SCN_MEM_DISCARDABLE, IMAGE_SCN_MEM_READ ]
Alignment: 1
SectionData: 04000000F10000005D0000002200011100000000433A5C63796777696E5C686F6D655C727569755C6E6F702E6F626A0037003C1103020000D00000000000000000000B00000027C601004D6963726F736F667420285229204D6163726F20417373656D626C65720000000000
symbols:
- Name: '@comp.id'
Value: 13485607
@@ -36,7 +36,7 @@ symbols:
StorageClass: IMAGE_SYM_CLASS_STATIC
SectionDefinition:
Length: 1
NumberOfRelocations: 0
NumberOfRelocations: 1
NumberOfLinenumbers: 0
CheckSum: 0
Number: 0
@@ -52,18 +52,12 @@ symbols:
NumberOfLinenumbers: 0
CheckSum: 0
Number: 0
- Name: '.debug$S'
- Name: __imp__fn
Value: 0
SectionNumber: 3
SectionNumber: 0
SimpleType: IMAGE_SYM_TYPE_NULL
ComplexType: IMAGE_SYM_DTYPE_NULL
StorageClass: IMAGE_SYM_CLASS_STATIC
SectionDefinition:
Length: 108
NumberOfRelocations: 0
NumberOfLinenumbers: 0
CheckSum: 0
Number: 0
StorageClass: IMAGE_SYM_CLASS_EXTERNAL
- Name: start
Value: 0
SectionNumber: 1

View File

@@ -1,7 +1,7 @@
# RUN: yaml2obj %p/Inputs/nop64.obj.yaml > %t.obj
# RUN: lld -flavor link /out:%t.exe /subsystem:console /entry:start \
# RUN: /machine:x64 -- %t.obj
# RUN: /machine:x64 -- %t.obj %p/Inputs/vars.lib
# RUN: llvm-readobj -file-headers %t.exe | FileCheck %s
CHECK: Format: COFF-x86-64
@@ -9,7 +9,7 @@ CHECK-NEXT: Arch: x86_64
CHECK-NEXT: AddressSize: 64bit
CHECK-NEXT: ImageFileHeader {
CHECK-NEXT: Machine: IMAGE_FILE_MACHINE_AMD64 (0x8664)
CHECK-NEXT: SectionCount: 1
CHECK-NEXT: SectionCount: 5
CHECK-NEXT: TimeDateStamp:
CHECK-NEXT: PointerToSymbolTable: 0x0
CHECK-NEXT: SymbolCount: 0
@@ -23,10 +23,10 @@ CHECK-NEXT: ImageOptionalHeader {
CHECK-NEXT: MajorLinkerVersion: 0
CHECK-NEXT: MinorLinkerVersion: 0
CHECK-NEXT: SizeOfCode: 512
CHECK-NEXT: SizeOfInitializedData: 0
CHECK-NEXT: SizeOfInitializedData: 2048
CHECK-NEXT: SizeOfUninitializedData: 0
CHECK-NEXT: AddressOfEntryPoint: 0x1000
CHECK-NEXT: BaseOfCode: 0x1000
CHECK-NEXT: AddressOfEntryPoint: 0x5000
CHECK-NEXT: BaseOfCode: 0x5000
CHECK-NEXT: ImageBase: 0x140000000
CHECK-NEXT: SectionAlignment: 4096
CHECK-NEXT: FileAlignment: 512
@@ -36,8 +36,8 @@ CHECK-NEXT: MajorImageVersion: 0
CHECK-NEXT: MinorImageVersion: 0
CHECK-NEXT: MajorSubsystemVersion: 6
CHECK-NEXT: MinorSubsystemVersion: 0
CHECK-NEXT: SizeOfImage: 8192
CHECK-NEXT: SizeOfHeaders: 512
CHECK-NEXT: SizeOfImage: 24576
CHECK-NEXT: SizeOfHeaders: 1024
CHECK-NEXT: Subsystem: IMAGE_SUBSYSTEM_WINDOWS_CUI (0x3)
CHECK-NEXT: Subsystem [ (0x8140)
CHECK-NEXT: IMAGE_DLL_CHARACTERISTICS_DYNAMIC_BASE (0x40)
@@ -52,8 +52,8 @@ CHECK-NEXT: NumberOfRvaAndSize: 16
CHECK-NEXT: DataDirectory {
CHECK-NEXT: ExportTableRVA: 0x0
CHECK-NEXT: ExportTableSize: 0x0
CHECK-NEXT: ImportTableRVA: 0x0
CHECK-NEXT: ImportTableSize: 0x0
CHECK-NEXT: ImportTableRVA: 0x3000
CHECK-NEXT: ImportTableSize: 0x28
CHECK-NEXT: ResourceTableRVA: 0x0
CHECK-NEXT: ResourceTableSize: 0x0
CHECK-NEXT: ExceptionTableRVA: 0x0
@@ -74,8 +74,8 @@ CHECK-NEXT: LoadConfigTableRVA: 0x0
CHECK-NEXT: LoadConfigTableSize: 0x0
CHECK-NEXT: BoundImportRVA: 0x0
CHECK-NEXT: BoundImportSize: 0x0
CHECK-NEXT: IATRVA: 0x0
CHECK-NEXT: IATSize: 0x0
CHECK-NEXT: IATRVA: 0x2000
CHECK-NEXT: IATSize: 0x10
CHECK-NEXT: DelayImportDescriptorRVA: 0x0
CHECK-NEXT: DelayImportDescriptorSize: 0x0
CHECK-NEXT: CLRRuntimeHeaderRVA: 0x0