summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorsagitario <sagitario@fc51e93f-b9fe-4711-8d8d-3ae870c5f7d8>2009-05-16 08:04:29 (GMT)
committersagitario <sagitario@fc51e93f-b9fe-4711-8d8d-3ae870c5f7d8>2009-05-16 08:04:29 (GMT)
commit1ebb42385c535860df1455656f39699bffb20937 (patch)
tree22b15aa4840c7ec051b3b9dde2e64158d650aa11 /src
parentd3adcbbc0c51ab693e7fcbd95569ffd548128d02 (diff)
downloadcv2pdb-1ebb42385c535860df1455656f39699bffb20937.zip
cv2pdb-1ebb42385c535860df1455656f39699bffb20937.tar.gz
cv2pdb-1ebb42385c535860df1455656f39699bffb20937.tar.bz2
v0.2:
some minor doc changes replace .debug section in executable rather than rename it, if it the last section. support for field type LF_VFUNCTAB and symbol type S_CONSTANT used by DMC. added stringview to autoexp.dat for full length text display.
Diffstat (limited to 'src')
-rw-r--r--src/PEImage.cpp66
-rw-r--r--src/PEImage.h2
-rw-r--r--src/cv2pdb.cpp25
3 files changed, 69 insertions, 24 deletions
diff --git a/src/PEImage.cpp b/src/PEImage.cpp
index ec826a8..d926078 100644
--- a/src/PEImage.cpp
+++ b/src/PEImage.cpp
@@ -10,6 +10,7 @@ extern "C" {
#include "mscvpdb.h"
}
+#include <stdio.h>
#include <io.h>
#include <fcntl.h>
#include <ctype.h>
@@ -59,7 +60,7 @@ bool PEImage::load(const char* iname)
close(fd);
fd = -1;
- return initPtr();
+ return initPtr(true);
}
///////////////////////////////////////////////////////////////////////
@@ -86,17 +87,9 @@ bool PEImage::save(const char* oname)
///////////////////////////////////////////////////////////////////////
bool PEImage::replaceDebugSection (const void* data, int datalen)
{
- int align = hdr->OptionalHeader.FileAlignment;
- int align_len = datalen;
- int fill = 0;
- if (align > 0)
- {
- fill = (align - (dump_total_len % align)) % align;
- align_len = ((datalen + align - 1) / align) * align;
- }
- char* newdata = (char*) alloc_aligned(dump_total_len + fill + datalen, 0x1000);
- if(!newdata)
- return setError("cannot alloc new image");
+ // append new debug directory to data
+ IMAGE_DEBUG_DIRECTORY debugdir = *dbgDir;
+ int xdatalen = datalen + sizeof(debugdir);
// assume there is place for another section because of section alignment
int s;
@@ -104,22 +97,43 @@ bool PEImage::replaceDebugSection (const void* data, int datalen)
for(s = 0; s < hdr->FileHeader.NumberOfSections; s++)
{
if (strcmp ((char*) sec [s].Name, ".debug") == 0)
+ {
+ if (s == hdr->FileHeader.NumberOfSections - 1)
+ {
+ dump_total_len = sec[s].PointerToRawData;
+ break;
+ }
strcpy ((char*) sec [s].Name, ".ddebug");
+ printf("warning: .debug not last section, cannot remove section\n");
+ }
lastVirtualAddress = sec [s].VirtualAddress + sec[s].Misc.VirtualSize;
}
- int salign_len = datalen;
+ int align = hdr->OptionalHeader.FileAlignment;
+ int align_len = xdatalen;
+ int fill = 0;
+
+ if (align > 0)
+ {
+ fill = (align - (dump_total_len % align)) % align;
+ align_len = ((xdatalen + align - 1) / align) * align;
+ }
+ char* newdata = (char*) alloc_aligned(dump_total_len + fill + xdatalen, 0x1000);
+ if(!newdata)
+ return setError("cannot alloc new image");
+
+ int salign_len = xdatalen;
align = hdr->OptionalHeader.SectionAlignment;
if (align > 0)
{
lastVirtualAddress = ((lastVirtualAddress + align - 1) / align) * align;
- salign_len = ((datalen + align - 1) / align) * align;
+ salign_len = ((xdatalen + align - 1) / align) * align;
}
strcpy((char*) sec[s].Name, ".debug");
sec[s].Misc.VirtualSize = align_len; // union with PhysicalAddress;
sec[s].VirtualAddress = lastVirtualAddress;
- sec[s].SizeOfRawData = datalen;
+ sec[s].SizeOfRawData = xdatalen;
sec[s].PointerToRawData = dump_total_len + fill;
sec[s].PointerToRelocations = 0;
sec[s].PointerToLinenumbers = 0;
@@ -127,27 +141,33 @@ bool PEImage::replaceDebugSection (const void* data, int datalen)
sec[s].NumberOfLinenumbers = 0;
sec[s].Characteristics = IMAGE_SCN_MEM_WRITE | IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_DISCARDABLE | IMAGE_SCN_CNT_INITIALIZED_DATA;
- hdr->FileHeader.NumberOfSections++;
- hdr->OptionalHeader.SizeOfImage += salign_len;
+ hdr->FileHeader.NumberOfSections = s + 1;
+ // hdr->OptionalHeader.SizeOfImage += salign_len;
+ hdr->OptionalHeader.SizeOfImage = sec[s].VirtualAddress + salign_len;
- dbgDir->PointerToRawData = sec[s].PointerToRawData;
- dbgDir->AddressOfRawData = sec[s].PointerToRawData;
- dbgDir->SizeOfData = sec[s].SizeOfRawData;
+ hdr->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress = lastVirtualAddress + datalen;
// append debug data chunk to existing file image
memcpy(newdata, dump_base, dump_total_len);
memset(newdata + dump_total_len, 0, fill);
memcpy(newdata + dump_total_len + fill, data, datalen);
+ dbgDir = (IMAGE_DEBUG_DIRECTORY*) (newdata + dump_total_len + fill + datalen);
+ memcpy(dbgDir, &debugdir, sizeof(debugdir));
+
+ dbgDir->PointerToRawData = sec[s].PointerToRawData;
+ dbgDir->AddressOfRawData = sec[s].PointerToRawData;
+ dbgDir->SizeOfData = sec[s].SizeOfRawData;
+
free_aligned(dump_base);
dump_base = newdata;
- dump_total_len += fill + datalen;
+ dump_total_len += fill + xdatalen;
- return initPtr();
+ return initPtr(false);
}
///////////////////////////////////////////////////////////////////////
-bool PEImage::initPtr()
+bool PEImage::initPtr(bool initDbgDir)
{
dos = DPV<IMAGE_DOS_HEADER> (0);
if(!dos)
diff --git a/src/PEImage.h b/src/PEImage.h
index bbc2eb9..df50395 100644
--- a/src/PEImage.h
+++ b/src/PEImage.h
@@ -58,7 +58,7 @@ public:
bool save(const char* oname);
bool replaceDebugSection (const void* data, int datalen);
- bool initPtr();
+ bool initPtr(bool initDbgDir);
int countCVEntries() const;
OMFDirEntry* getCVEntry(int i) const;
diff --git a/src/cv2pdb.cpp b/src/cv2pdb.cpp
index b1a932d..bb91af7 100644
--- a/src/cv2pdb.cpp
+++ b/src/cv2pdb.cpp
@@ -489,6 +489,18 @@ int CV2PDB::addFields(codeview_reftype* dfieldlist, const codeview_reftype* fiel
copylen += strlen(fieldtype->nesttype_v3.name) + 1;
break;
+ case LF_VFUNCTAB_V1:
+ dfieldtype->vfunctab_v2.id = LF_VFUNCTAB_V2;
+ dfieldtype->vfunctab_v2.type = fieldtype->vfunctab_v1.type;
+ dfieldtype->vfunctab_v2._pad0 = 0;
+ pos += sizeof(fieldtype->vfunctab_v1);
+ dpos += sizeof(dfieldtype->vfunctab_v2);
+ break;
+
+ case LF_VFUNCTAB_V2:
+ copylen = sizeof(dfieldtype->vfunctab_v2);
+ break;
+
default:
setError("unsupported field entry");
break;
@@ -1773,6 +1785,7 @@ int CV2PDB::copySymbols(BYTE* srcSymbols, int srcSize, BYTE* destSymbols, int de
{
codeview_symbol* lastGProcSym = 0;
int type, length, destlength;
+ int leaf_len, value;
for (int i = 0; i < srcSize; i += length)
{
codeview_symbol* sym = (codeview_symbol*)(srcSymbols + i);
@@ -1885,9 +1898,21 @@ int CV2PDB::copySymbols(BYTE* srcSymbols, int srcSize, BYTE* destSymbols, int de
destSize += 4;
break;
+ case S_CONSTANT_V1:
+ dsym->constant_v2.id = v3 ? S_CONSTANT_V3 : S_CONSTANT_V2;
+ dsym->constant_v2.type = sym->constant_v1.type;
+ leaf_len = numeric_leaf(&value, &sym->constant_v1.cvalue);
+ memcpy(&dsym->constant_v2.cvalue, &sym->constant_v1.cvalue, leaf_len);
+ destlength = pstrcpy_v (v3, (BYTE*) &dsym->constant_v2.cvalue + leaf_len,
+ (BYTE*) &sym->constant_v1.cvalue + leaf_len);
+ destlength += sizeof(dsym->constant_v2) - sizeof(dsym->constant_v2.cvalue) + leaf_len;
+ dsym->constant_v2.len = destlength - 2;
+ break;
+
case S_ALIGN_V1:
continue; // throw away
break;
+
default:
sym = sym;
break;