mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2025-01-19 07:50:08 +00:00
Merge remote-tracking branch 'origin/GP-2827_ryanmkurtz_pe-imagebase'
(Closes #2361, Closes #4710)
This commit is contained in:
commit
102d1b7151
@ -267,10 +267,6 @@ public interface OptionalHeader extends StructConverter {
|
||||
*/
|
||||
public long getImageBase();
|
||||
|
||||
public long getOriginalImageBase();
|
||||
|
||||
public boolean wasRebased();
|
||||
|
||||
/**
|
||||
* @return the RVA that would be assigned to the next section following the last section
|
||||
*/
|
||||
|
@ -143,9 +143,6 @@ public class OptionalHeaderImpl implements OptionalHeader {
|
||||
protected int startIndex;
|
||||
private long startOfDataDirs;
|
||||
|
||||
protected long originalImageBase;
|
||||
protected boolean wasRebased;
|
||||
|
||||
OptionalHeaderImpl(NTHeader ntHeader, BinaryReader reader, int startIndex) throws IOException {
|
||||
this.ntHeader = ntHeader;
|
||||
this.reader = reader;
|
||||
@ -182,11 +179,6 @@ public class OptionalHeaderImpl implements OptionalHeader {
|
||||
return imageBase;
|
||||
}
|
||||
|
||||
@Override
|
||||
public long getOriginalImageBase() {
|
||||
return originalImageBase;
|
||||
}
|
||||
|
||||
@Override
|
||||
public long getAddressOfEntryPoint() {
|
||||
return Conv.intToLong(addressOfEntryPoint);
|
||||
@ -515,23 +507,10 @@ public class OptionalHeaderImpl implements OptionalHeader {
|
||||
if (is64bit()) {
|
||||
baseOfData = -1;//not used
|
||||
imageBase = reader.readNextLong();
|
||||
if (imageBase <= 0 && !is64bit()) {
|
||||
Msg.warn(this, "Non-standard image base: 0x" + Long.toHexString(imageBase));
|
||||
originalImageBase = imageBase;
|
||||
imageBase = 0x10000;
|
||||
wasRebased = true;
|
||||
}
|
||||
}
|
||||
else {
|
||||
baseOfData = reader.readNextInt();
|
||||
int imgBase = reader.readNextInt();
|
||||
imageBase = imgBase & Conv.INT_MASK;
|
||||
if (imgBase <= 0) {
|
||||
Msg.warn(this, "Non-standard image base " + Integer.toHexString(imgBase));
|
||||
originalImageBase = imageBase;
|
||||
imageBase = 0x10000;
|
||||
wasRebased = true;
|
||||
}
|
||||
imageBase = Integer.toUnsignedLong(reader.readNextInt());
|
||||
}
|
||||
|
||||
sectionAlignment = reader.readNextInt();
|
||||
@ -744,11 +723,6 @@ public class OptionalHeaderImpl implements OptionalHeader {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean wasRebased() {
|
||||
return wasRebased;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isCLI() throws IOException {
|
||||
long origPointerIndex = reader.getPointerIndex();
|
||||
|
@ -36,13 +36,12 @@ import ghidra.program.database.mem.FileBytes;
|
||||
import ghidra.program.model.address.*;
|
||||
import ghidra.program.model.data.*;
|
||||
import ghidra.program.model.listing.*;
|
||||
import ghidra.program.model.mem.Memory;
|
||||
import ghidra.program.model.mem.MemoryAccessException;
|
||||
import ghidra.program.model.reloc.RelocationTable;
|
||||
import ghidra.program.model.symbol.*;
|
||||
import ghidra.program.model.util.AddressSetPropertyMap;
|
||||
import ghidra.program.model.util.CodeUnitInsertionException;
|
||||
import ghidra.util.*;
|
||||
import ghidra.util.Msg;
|
||||
import ghidra.util.exception.*;
|
||||
import ghidra.util.task.TaskMonitor;
|
||||
|
||||
@ -281,10 +280,9 @@ public class PeLoader extends AbstractPeDebugLoader {
|
||||
|
||||
private void processRelocations(OptionalHeader optionalHeader, Program prog,
|
||||
TaskMonitor monitor, MessageLog log) {
|
||||
// We don't currently support relocations in PE's because we always load at the preferred
|
||||
// image base, but we'll go though them anyway and add them to the relocation table
|
||||
|
||||
if (monitor.isCancelled()) {
|
||||
return;
|
||||
}
|
||||
monitor.setMessage("[" + prog.getName() + "]: processing relocation tables...");
|
||||
|
||||
DataDirectory[] dataDirectories = optionalHeader.getDataDirectories();
|
||||
@ -300,68 +298,14 @@ public class PeLoader extends AbstractPeDebugLoader {
|
||||
AddressSpace space = prog.getAddressFactory().getDefaultAddressSpace();
|
||||
RelocationTable relocTable = prog.getRelocationTable();
|
||||
|
||||
Memory memory = prog.getMemory();
|
||||
|
||||
BaseRelocation[] relocs = brdd.getBaseRelocations();
|
||||
long originalImageBase = optionalHeader.getOriginalImageBase();
|
||||
AddressRange brddRange =
|
||||
new AddressRangeImpl(space.getAddress(originalImageBase + brdd.getVirtualAddress()),
|
||||
space.getAddress(originalImageBase + brdd.getVirtualAddress() + brdd.getSize()));
|
||||
AddressRange headerRange = new AddressRangeImpl(space.getAddress(originalImageBase),
|
||||
space.getAddress(originalImageBase + optionalHeader.getSizeOfHeaders()));
|
||||
DataConverter conv = LittleEndianDataConverter.INSTANCE;
|
||||
|
||||
for (BaseRelocation reloc : relocs) {
|
||||
for (BaseRelocation reloc : brdd.getBaseRelocations()) {
|
||||
if (monitor.isCancelled()) {
|
||||
return;
|
||||
}
|
||||
int baseAddr = reloc.getVirtualAddress();
|
||||
int count = reloc.getCount();
|
||||
for (int j = 0; j < count; ++j) {
|
||||
int type = reloc.getType(j);
|
||||
if (type == BaseRelocation.IMAGE_REL_BASED_ABSOLUTE) {
|
||||
continue;
|
||||
}
|
||||
int offset = reloc.getOffset(j);
|
||||
long addr =
|
||||
Integer.toUnsignedLong(baseAddr + offset) + optionalHeader.getImageBase();
|
||||
Address relocAddr = space.getAddress(addr);
|
||||
|
||||
try {
|
||||
byte[] bytes = optionalHeader.is64bit() ? new byte[8] : new byte[4];
|
||||
memory.getBytes(relocAddr, bytes);
|
||||
if (optionalHeader.wasRebased()) {
|
||||
long val = optionalHeader.is64bit() ? conv.getLong(bytes)
|
||||
: conv.getInt(bytes) & 0xFFFFFFFFL;
|
||||
val =
|
||||
val - (originalImageBase & 0xFFFFFFFFL) + optionalHeader.getImageBase();
|
||||
byte[] newbytes = optionalHeader.is64bit() ? conv.getBytes(val)
|
||||
: conv.getBytes((int) val);
|
||||
if (type == BaseRelocation.IMAGE_REL_BASED_HIGHLOW) {
|
||||
memory.setBytes(relocAddr, newbytes);
|
||||
}
|
||||
else if (type == BaseRelocation.IMAGE_REL_BASED_DIR64) {
|
||||
memory.setBytes(relocAddr, newbytes);
|
||||
}
|
||||
else {
|
||||
Msg.error(this, "Non-standard relocation type " + type);
|
||||
}
|
||||
}
|
||||
|
||||
relocTable.add(relocAddr, type, null, null, null);
|
||||
|
||||
}
|
||||
catch (MemoryAccessException e) {
|
||||
log.appendMsg("Relocation does not exist in memory: " + relocAddr);
|
||||
}
|
||||
if (brddRange.contains(relocAddr)) {
|
||||
Msg.error(this, "Self-modifying relocation table at " + relocAddr);
|
||||
return;
|
||||
}
|
||||
if (headerRange.contains(relocAddr)) {
|
||||
Msg.error(this, "Header modified at " + relocAddr);
|
||||
return;
|
||||
}
|
||||
for (int i = 0; i < reloc.getCount(); ++i) {
|
||||
long addr = optionalHeader.getImageBase() + baseAddr + reloc.getOffset(i);
|
||||
relocTable.add(space.getAddress(addr), reloc.getType(i), null, null, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user