mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2026-09-28 17:11:11 -09:00
GP-4737 - Improve ELF relocation handling of unresolved symbol
This commit is contained in:
@@ -62,15 +62,11 @@ public class PowerPC64_ElfRelocationHandler
|
||||
|
||||
Program program = elfRelocationContext.getProgram();
|
||||
Memory memory = program.getMemory();
|
||||
|
||||
|
||||
// NOTE: Based upon glibc source it appears that PowerPC only uses RELA relocations
|
||||
long addend = relocation.getAddend();
|
||||
|
||||
long offset = relocationAddress.getOffset();
|
||||
int symbolIndex = relocation.getSymbolIndex();
|
||||
int oldValue = memory.getInt(relocationAddress);
|
||||
int newValue = 0;
|
||||
int byteLength = 4; // most relocations affect 4-bytes (change if different)
|
||||
|
||||
// IMPORTANT NOTE:
|
||||
// Handling of Object modules (*.o) is currently problematic since relocations
|
||||
@@ -102,12 +98,40 @@ public class PowerPC64_ElfRelocationHandler
|
||||
break;
|
||||
default:
|
||||
}
|
||||
|
||||
|
||||
// Handle relative relocations that do not require symbolAddr or symbolValue
|
||||
switch (type) {
|
||||
|
||||
case R_PPC64_RELATIVE:
|
||||
long value64 = elfRelocationContext.getImageBaseWordAdjustmentOffset() + addend;
|
||||
memory.setLong(relocationAddress, value64);
|
||||
return new RelocationResult(Status.APPLIED, 8);
|
||||
|
||||
case R_PPC64_TOC:
|
||||
memory.setLong(relocationAddress, toc);
|
||||
return new RelocationResult(Status.APPLIED, 8);
|
||||
|
||||
case R_PPC64_COPY:
|
||||
markAsUnsupportedCopy(program, relocationAddress, type, symbolName, symbolIndex,
|
||||
sym.getSize(), elfRelocationContext.getLog());
|
||||
return RelocationResult.UNSUPPORTED;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
// Check for unresolved symbolAddr and symbolValue required by remaining relocation types handled below
|
||||
if (handleUnresolvedSymbol(elfRelocationContext, relocation, relocationAddress)) {
|
||||
return RelocationResult.FAILURE;
|
||||
}
|
||||
|
||||
int oldValue = memory.getInt(relocationAddress);
|
||||
int newValue = 0;
|
||||
|
||||
int byteLength = 4; // most relocations affect 4-bytes (change if different)
|
||||
|
||||
switch (type) {
|
||||
|
||||
case R_PPC64_ADDR32:
|
||||
newValue = (int) (symbolValue + addend);
|
||||
memory.setInt(relocationAddress, newValue);
|
||||
@@ -179,11 +203,6 @@ public class PowerPC64_ElfRelocationHandler
|
||||
newValue = (oldValue & ~PPC64_LOW24) | newValue;
|
||||
memory.setInt(relocationAddress, newValue);
|
||||
break;
|
||||
case R_PPC64_RELATIVE:
|
||||
long value64 = elfRelocationContext.getImageBaseWordAdjustmentOffset() + addend;
|
||||
memory.setLong(relocationAddress, value64);
|
||||
byteLength = 8;
|
||||
break;
|
||||
case R_PPC64_REL32:
|
||||
newValue = (int) (symbolValue + addend - offset);
|
||||
memory.setInt(relocationAddress, newValue);
|
||||
@@ -230,7 +249,7 @@ public class PowerPC64_ElfRelocationHandler
|
||||
case R_PPC64_UADDR64:
|
||||
case R_PPC64_ADDR64:
|
||||
case R_PPC64_GLOB_DAT:
|
||||
value64 = symbolValue + addend;
|
||||
long value64 = symbolValue + addend;
|
||||
memory.setLong(relocationAddress, value64);
|
||||
byteLength = 8;
|
||||
if (symbolIndex != 0 && addend != 0 && !sym.isSection()) {
|
||||
@@ -239,10 +258,6 @@ public class PowerPC64_ElfRelocationHandler
|
||||
applyComponentOffsetPointer(program, relocationAddress, addend);
|
||||
}
|
||||
break;
|
||||
case R_PPC64_TOC:
|
||||
memory.setLong(relocationAddress, toc);
|
||||
byteLength = 8;
|
||||
break;
|
||||
default:
|
||||
markAsUnhandled(program, relocationAddress, type, symbolIndex, symbolName,
|
||||
elfRelocationContext.getLog());
|
||||
|
||||
@@ -71,6 +71,33 @@ public class PowerPC_ElfRelocationHandler extends
|
||||
|
||||
// NOTE: Based upon glibc source it appears that PowerPC only uses RELA relocations
|
||||
int addend = (int) relocation.getAddend();
|
||||
|
||||
long relocbase = elfRelocationContext.getImageBaseWordAdjustmentOffset();
|
||||
|
||||
int newValue = 0;
|
||||
int byteLength = 4; // most relocations affect 4-bytes (change if different)
|
||||
|
||||
// Handle relative relocations that do not require symbolAddr or symbolValue
|
||||
switch (type) {
|
||||
|
||||
case R_PPC_RELATIVE:
|
||||
newValue = (int) relocbase + addend;
|
||||
memory.setInt(relocationAddress, newValue);
|
||||
return new RelocationResult(Status.APPLIED, byteLength);
|
||||
|
||||
case R_PPC_COPY:
|
||||
markAsUnsupportedCopy(program, relocationAddress, type, symbolName, symbolIndex,
|
||||
sym.getSize(), elfRelocationContext.getLog());
|
||||
return RelocationResult.UNSUPPORTED;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
// Check for unresolved symbolAddr and symbolValue required by remaining relocation types handled below
|
||||
if (handleUnresolvedSymbol(elfRelocationContext, relocation, relocationAddress)) {
|
||||
return RelocationResult.FAILURE;
|
||||
}
|
||||
|
||||
// if (sym.isLocal() && sym.getSectionHeaderIndex() != ElfSectionHeaderConstants.SHN_UNDEF) {
|
||||
//
|
||||
@@ -83,18 +110,11 @@ public class PowerPC_ElfRelocationHandler extends
|
||||
// symbolValue = elfRelocationContext.getImageBaseWordAdjustmentOffset();
|
||||
// }
|
||||
|
||||
long relocbase = elfRelocationContext.getImageBaseWordAdjustmentOffset();
|
||||
|
||||
int offset = (int) relocationAddress.getOffset();
|
||||
int oldValue = memory.getInt(relocationAddress);
|
||||
int newValue = 0;
|
||||
int byteLength = 4; // most relocations affect 4-bytes (change if different)
|
||||
|
||||
switch (type) {
|
||||
case R_PPC_COPY:
|
||||
markAsUnsupportedCopy(program, relocationAddress, type, symbolName, symbolIndex,
|
||||
sym.getSize(), elfRelocationContext.getLog());
|
||||
return RelocationResult.UNSUPPORTED;
|
||||
|
||||
case R_PPC_ADDR32:
|
||||
case R_PPC_UADDR32:
|
||||
case R_PPC_GLOB_DAT:
|
||||
@@ -162,10 +182,6 @@ public class PowerPC_ElfRelocationHandler extends
|
||||
newValue = (oldValue & ~PPC_LOW24) | newValue;
|
||||
memory.setInt(relocationAddress, newValue);
|
||||
break;
|
||||
case R_PPC_RELATIVE:
|
||||
newValue = (int) elfRelocationContext.getImageBaseWordAdjustmentOffset() + addend;
|
||||
memory.setInt(relocationAddress, newValue);
|
||||
break;
|
||||
case R_PPC_REL32:
|
||||
newValue = ((int) symbolValue + addend - offset);
|
||||
memory.setInt(relocationAddress, newValue);
|
||||
@@ -216,8 +232,7 @@ public class PowerPC_ElfRelocationHandler extends
|
||||
|
||||
oldValue = memory.getInt(relocationAddress);
|
||||
|
||||
Address symAddr = elfRelocationContext.getSymbolAddress(sym);
|
||||
MemoryBlock block = memory.getBlock(symAddr);
|
||||
MemoryBlock block = memory.getBlock(symbolAddr);
|
||||
Integer sdaBase = null;
|
||||
Integer gprID = null;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user