mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2024-11-21 19:42:14 +00:00
Merge remote-tracking branch 'origin/GP-2052_ryanmkurtz_prelink'
This commit is contained in:
commit
0241b2b97e
@ -139,11 +139,12 @@ public class MachHeader implements StructConverter {
|
||||
if (_parsed) {
|
||||
return this;
|
||||
}
|
||||
long currentIndex = _commandIndex;
|
||||
for (int i = 0; i < nCmds; ++i) {
|
||||
_reader.setPointerIndex(_commandIndex);
|
||||
_reader.setPointerIndex(currentIndex);
|
||||
LoadCommand lc = LoadCommandTypes.getLoadCommand(_reader, this);
|
||||
_commands.add(lc);
|
||||
_commandIndex += lc.getCommandSize();
|
||||
currentIndex += lc.getCommandSize();
|
||||
}
|
||||
_parsed = true;
|
||||
return this;
|
||||
@ -289,6 +290,15 @@ public class MachHeader implements StructConverter {
|
||||
return magic == MachConstants.MH_CIGAM || magic == MachConstants.MH_CIGAM_64;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the size of this {@link MachHeader} in bytes
|
||||
*
|
||||
* @return The size of this {@link MachHeader} in bytes
|
||||
*/
|
||||
public long getSize() {
|
||||
return _commandIndex - _machHeaderStartIndexInProvider;
|
||||
}
|
||||
|
||||
public String getDescription() {//TODO
|
||||
StringBuffer buffer = new StringBuffer();
|
||||
buffer.append("Magic: 0x" + Integer.toHexString(magic));
|
||||
|
@ -22,8 +22,7 @@ import org.apache.commons.collections4.BidiMap;
|
||||
import org.apache.commons.collections4.bidimap.DualHashBidiMap;
|
||||
import org.jdom.JDOMException;
|
||||
|
||||
import ghidra.app.util.bin.ByteProvider;
|
||||
import ghidra.app.util.bin.ByteProviderWrapper;
|
||||
import ghidra.app.util.bin.*;
|
||||
import ghidra.app.util.bin.format.macho.MachException;
|
||||
import ghidra.app.util.bin.format.macho.MachHeader;
|
||||
import ghidra.app.util.bin.format.macho.commands.*;
|
||||
@ -36,6 +35,42 @@ import ghidra.util.task.TaskMonitor;
|
||||
*/
|
||||
public class MachoPrelinkUtils {
|
||||
|
||||
/**
|
||||
* Check to see if the given {@link ByteProvider} is a Mach-O PRELINK binary
|
||||
*
|
||||
* @param provider The {@link ByteProvider} to check
|
||||
* @param monitor A monitor
|
||||
* @return True if the given {@link ByteProvider} is a Mach-O PRELINK binary; otherwise, false
|
||||
*/
|
||||
public static boolean isMachoPrelink(ByteProvider provider, TaskMonitor monitor) {
|
||||
try {
|
||||
MachHeader header = new MachHeader(provider);
|
||||
BinaryReader reader = new BinaryReader(provider, header.isLittleEndian());
|
||||
reader.setPointerIndex(header.getSize());
|
||||
|
||||
// Doing a full header parse is too slow...we really just need to see if a segment
|
||||
// exists that starts with __PRELINK. Parse the minimal amount to do that check.
|
||||
for (int i = 0; i < header.getNumberOfCommands(); i++) {
|
||||
int type = reader.peekNextInt();
|
||||
if (type == LoadCommandTypes.LC_SEGMENT || type == LoadCommandTypes.LC_SEGMENT_64) {
|
||||
SegmentCommand segment = new SegmentCommand(reader, header.is32bit());
|
||||
if (segment.getSegmentName().startsWith("__PRELINK")) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else {
|
||||
type = reader.readNextInt();
|
||||
int size = reader.readNextInt();
|
||||
reader.setPointerIndex(reader.getPointerIndex() + size - 8);
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (MachException | IOException e) {
|
||||
// Assume it's not a Mach-O PRELINK...fall through
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses the provider looking for PRELINK XML.
|
||||
*
|
||||
|
@ -15,10 +15,9 @@
|
||||
*/
|
||||
package ghidra.file.formats.ios.prelink;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.util.*;
|
||||
|
||||
import org.apache.commons.collections4.BidiMap;
|
||||
import org.jdom.JDOMException;
|
||||
@ -76,18 +75,7 @@ public class PrelinkFileSystem extends GFileSystemBase implements GFileSystemPro
|
||||
|
||||
@Override
|
||||
public boolean isValid(TaskMonitor monitor) throws IOException {
|
||||
try {
|
||||
return MachHeader.isMachHeader(provider) &&
|
||||
!MachoPrelinkUtils.parsePrelinkXml(provider, monitor).isEmpty();
|
||||
}
|
||||
catch (JDOMException e) {
|
||||
Msg.warn(this, e.getMessage());
|
||||
return true; // use KModInfo technique to open
|
||||
}
|
||||
catch (IOException e) {
|
||||
Msg.warn(this, e.getMessage());
|
||||
return false;
|
||||
}
|
||||
return MachoPrelinkUtils.isMachoPrelink(provider, monitor);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
Loading…
Reference in New Issue
Block a user