obj2yaml, yaml2obj: Add support for COFF executables

In support of serializing executables, obj2yaml now records the virtual address
and size of sections.  It also serializes whatever we strictly need from
the PE header, it expects that it can reconstitute everything else via
inference.

yaml2obj can reconstitute a fully linked executable.

In order to get executables correctly serialized/deserialized, other
bugs were fixed as a circumstance.  We now properly respect file and
section alignments.  We also avoid writing out string tables unless they
are strictly necessary.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@221975 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
David Majnemer
2014-11-14 08:15:42 +00:00
parent dada992be7
commit 237544b16d
7 changed files with 393 additions and 52 deletions

View File

@ -460,9 +460,9 @@ std::error_code COFFObjectFile::initSymbolTablePtr() {
// Find string table. The first four byte of the string table contains the
// total size of the string table, including the size field itself. If the
// string table is empty, the value of the first four byte would be 4.
const uint8_t *StringTableAddr =
base() + getPointerToSymbolTable() +
getNumberOfSymbols() * getSymbolTableEntrySize();
uint32_t StringTableOffset = getPointerToSymbolTable() +
getNumberOfSymbols() * getSymbolTableEntrySize();
const uint8_t *StringTableAddr = base() + StringTableOffset;
const ulittle32_t *StringTableSizePtr;
if (std::error_code EC = getObject(StringTableSizePtr, Data, StringTableAddr))
return EC;
@ -826,13 +826,17 @@ std::error_code
COFFObjectFile::getDataDirectory(uint32_t Index,
const data_directory *&Res) const {
// Error if if there's no data directory or the index is out of range.
if (!DataDirectory)
if (!DataDirectory) {
Res = nullptr;
return object_error::parse_failed;
}
assert(PE32Header || PE32PlusHeader);
uint32_t NumEnt = PE32Header ? PE32Header->NumberOfRvaAndSize
: PE32PlusHeader->NumberOfRvaAndSize;
if (Index > NumEnt)
if (Index >= NumEnt) {
Res = nullptr;
return object_error::parse_failed;
}
Res = &DataDirectory[Index];
return object_error::success;
}