ghidra.program.model.listing.ContextChangeException Java Examples

The following examples show how to use ghidra.program.model.listing.ContextChangeException. You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: ARM_ElfExtension.java    From ghidra with Apache License 2.0 6 votes vote down vote up
@Override
public Address creatingFunction(ElfLoadHelper elfLoadHelper, Address functionAddress) {
	Program program = elfLoadHelper.getProgram();
	if ((functionAddress.getOffset() & 1) != 0) {
		Register tmodeRegister = program.getRegister("TMode");
		if (tmodeRegister == null) {
			elfLoadHelper.log("TMode mode not supported, unable to mark address as Thumb: " +
				functionAddress);
			return functionAddress;
		}
		functionAddress = functionAddress.previous(); // align address
		try {
			program.getProgramContext().setValue(tmodeRegister, functionAddress,
				functionAddress, BigInteger.ONE);
		}
		catch (ContextChangeException e) {
			// ignore since should not be instructions at time of import
		}
	}
	if ((functionAddress.getOffset() % 4) == 2) {//The combination bit[1:0] = 0b10 is reserved.
		elfLoadHelper.log("Function address is two bit aligned (reserved per ARM manual): " +
			functionAddress);
	}
	return functionAddress;
}
 
Example #2
Source File: DisassemblerContextImpl.java    From ghidra with Apache License 2.0 6 votes vote down vote up
/**
	 * Saves the context from the startAddr (inclusive) to the end address (inclusive)
	 * back to the program's stored context.
	 * @param startAddress 
	 * @param endAddress 
	 */
	private void saveProgramContext(Address start, Address end) {
		if (end == null || start.compareTo(end) > 0) {
			throw new IllegalArgumentException("Invalid context range: (" + start + "," + end + ")");
		}

// TODO: Should disassembler context be used for anything other than the context-register ??

		Iterator<Register> it = registerStateMap.keySet().iterator();
		while (it.hasNext()) {
			Register reg = it.next();
			if (reg.isProcessorContext()) {
				continue;
			}
			RegisterValue value = registerStateMap.get(reg);
			try {
				programContext.setRegisterValue(start, end, value);
			}
			catch (ContextChangeException e) {
				// we should never be writing the context register
			}
		}
	}
 
Example #3
Source File: AbstractStoredProgramContext.java    From ghidra with Apache License 2.0 6 votes vote down vote up
@Override
public void setRegisterValue(Address start, Address end, RegisterValue value)
		throws ContextChangeException {
	if (value == null) {
		throw new IllegalArgumentException("Value cannot be null, use remove() instead!");
	}
	Register baseRegister = value.getRegister().getBaseRegister();
	RegisterValueStore store = registerValueMap.get(baseRegister);
	if (store == null) {
		RangeMapAdapter adapter = createNewRangeMapAdapter(baseRegister);
		store = createRegisterValueStore(baseRegister, adapter);
	}
	store.setValue(start, end, value);
	if (registersWithValues != null && !registersWithValues.contains(baseRegister)) {
		addRegisterWithValue(baseRegister);
	}
}
 
Example #4
Source File: PseudoDisassembler.java    From ghidra with Apache License 2.0 6 votes vote down vote up
/**
 * If this processor uses the low bit of an address to change to a new Instruction Set mode
 *   Check the low bit and change the instruction state at the address.
 *   
 * @param program
 * @param addr the raw address
 * @return the correct address to disassemble at if it needs to be aligned
 */
public static Address setTargeContextForDisassembly(Program program, Address addr) {
	Register lowBitCodeMode = program.getRegister(LOW_BIT_CODE_MODE_REGISTER_NAME);
	if (lowBitCodeMode == null) {
		return addr;
	}
	long offset = addr.getOffset();
	if ((offset & 1) == 1) {
		addr = addr.getNewAddress(addr.getOffset() & ~0x1);
		try {
			program.getProgramContext().setValue(lowBitCodeMode, addr, addr, BigInteger.ONE);
		}
		catch (ContextChangeException e) {
			// shouldn't happen
		}
	}
	return addr;
}
 
Example #5
Source File: ProgramRegisterContextDB.java    From ghidra with Apache License 2.0 6 votes vote down vote up
@Override
public void remove(Address start, Address end, Register register)
		throws ContextChangeException {
	lock.acquire();
	boolean restore = false;
	try {
		checkContextWrite(register, start, end);
		restore = !changing; // indicates that we just initiated a change
		changing = true;
		super.remove(start, end, register);
		if (program != null) {
			program.setRegisterValuesChanged(register, start, end);
		}
	}
	finally {
		if (restore) {
			changing = false;
		}
		lock.release();
	}
}
 
Example #6
Source File: ProgramRegisterContextDB.java    From ghidra with Apache License 2.0 6 votes vote down vote up
@Override
public void setValue(Register register, Address start, Address end, BigInteger value)
		throws ContextChangeException {
	lock.acquire();
	boolean restore = false;
	try {
		checkContextWrite(register, start, end);
		restore = !changing; // indicates that we just initiated a change
		changing = true;
		super.setValue(register, start, end, value);
		if (program != null) {
			program.setRegisterValuesChanged(register, start, end);
		}
	}
	finally {
		if (restore) {
			changing = false;
		}
		lock.release();
	}

}
 
Example #7
Source File: ProgramRegisterContextDB.java    From ghidra with Apache License 2.0 6 votes vote down vote up
@Override
public void setRegisterValue(Address start, Address end, RegisterValue value)
		throws ContextChangeException {
	lock.acquire();
	boolean restore = false;
	try {
		// FIXME: We do not properly handle painting context across the full 
		// address space which should be avoided.  A non-zero image
		// base offset can result in a improperly coalesced long key-range.
		checkContextWrite(value.getRegister(), start, end);
		restore = !changing; // indicates that we just initiated a change
		changing = true;
		super.setRegisterValue(start, end, value);
		if (program != null) {
			program.setRegisterValuesChanged(value.getRegister(), start, end);
		}
	}
	finally {
		if (restore) {
			changing = false;
		}
		lock.release();
	}
}
 
Example #8
Source File: ProgramRegisterContextDB.java    From ghidra with Apache License 2.0 6 votes vote down vote up
private void fillInContextGaps(Register ctxReg, RegisterValue gapValue,
		AddressSetView programMemory) {

	AddressSet area = new AddressSet(programMemory);

	RegisterValueStore store = registerValueMap.get(ctxReg);
	if (store != null) {
		AddressRangeIterator addressRangeIterator = store.getAddressRangeIterator();
		while (addressRangeIterator.hasNext()) {
			area.delete(addressRangeIterator.next());
		}
	}
	AddressRangeIterator addressRanges = area.getAddressRanges();
	while (addressRanges.hasNext()) {
		AddressRange range = addressRanges.next();
		try {
			setRegisterValue(range.getMinAddress(), range.getMaxAddress(), gapValue);
		}
		catch (ContextChangeException e) {
			throw new AssertException("Unexpected context error during language upgrade", e);
		}
	}

}
 
Example #9
Source File: AbstractStoredProgramContext.java    From ghidra with Apache License 2.0 5 votes vote down vote up
@Override
public void setValue(Register register, Address start, Address end, BigInteger value)
		throws ContextChangeException {
	if (start.getAddressSpace() != end.getAddressSpace()) {
		throw new AssertException("start and end address must be in the same address space");
	}
	if (value == null) {
		remove(start, end, register);
		return;
	}
	setRegisterValue(start, end, new RegisterValue(register, value));
}
 
Example #10
Source File: AbstractStoredProgramContext.java    From ghidra with Apache License 2.0 5 votes vote down vote up
@Override
public void remove(Address start, Address end, Register register)
		throws ContextChangeException {
	if (start.getAddressSpace() != end.getAddressSpace()) {
		throw new AssertException("start and end address must be in the same address space");
	}
	RegisterValueStore values = registerValueMap.get(register.getBaseRegister());
	if (values != null) {
		values.clearValue(start, end, register);
	}
	invalidateReadCache();
}
 
Example #11
Source File: ProgramRegisterContextDB.java    From ghidra with Apache License 2.0 5 votes vote down vote up
private void recoverOldRegisterValue(Address start, Address end, RegisterValue value) {

		Register reg = value.getRegister();

		if (reg.isProcessorContext()) {
			if (!reg.hasChildren()) {
				return; // no context fields defined
			}
			byte[] validBitMask = reg.getBaseMask();
			Arrays.fill(validBitMask, (byte) 0);
			for (Register child : reg.getChildRegisters()) {
				byte[] mask = child.getBaseMask();
				for (int i = 0; i < validBitMask.length; i++) {
					validBitMask[i] |= mask[i];
				}
			}
			byte[] maskValue = value.toBytes();
			for (int i = 0; i < validBitMask.length; i++) {
				maskValue[i] &= validBitMask[i];
				maskValue[i + validBitMask.length] &= validBitMask[i];
			}
			value = new RegisterValue(reg, maskValue);
		}

		try {
			setRegisterValue(start, end, value);
		}
		catch (ContextChangeException e) {
			throw new AssertException("Unexpected context error during upgrade", e);
		}
	}
 
Example #12
Source File: ProgramRegisterContextDB.java    From ghidra with Apache License 2.0 5 votes vote down vote up
private void checkContextWrite(Register reg, Address start, Address end)
		throws ContextChangeException {
	if (changing || !reg.getBaseRegister().equals(getBaseContextRegister())) {
		return;
	}
	CodeManager codeManager = program.getCodeManager();
	codeManager.checkContextWrite(start, end);
}
 
Example #13
Source File: ProgramContextMergeManagerTest.java    From ghidra with Apache License 2.0 4 votes vote down vote up
private void setRegValue(ProgramContext pc, Address start, Address end, Register reg,
		long value) throws ContextChangeException {
	BigInteger bi = BigInteger.valueOf(value);
	pc.setValue(reg, start, end, bi);
}
 
Example #14
Source File: ProgramProcessorContext.java    From ghidra with Apache License 2.0 4 votes vote down vote up
@Override
public void clearRegister(Register register) throws ContextChangeException {
	context.remove(addr, addr, register);
}
 
Example #15
Source File: ProgramProcessorContext.java    From ghidra with Apache License 2.0 4 votes vote down vote up
@Override
public void setRegisterValue(RegisterValue value) throws ContextChangeException {
	context.setRegisterValue(addr, addr, value);
}
 
Example #16
Source File: ProgramProcessorContext.java    From ghidra with Apache License 2.0 4 votes vote down vote up
/**
 * @throws ContextChangeException 
 * @see ghidra.program.model.lang.ProcessorContext#setValue(ghidra.program.model.lang.Register, java.math.BigInteger)
 */
@Override
public void setValue(Register register, BigInteger value) throws ContextChangeException {
	context.setValue(register, addr, addr, value);
}
 
Example #17
Source File: AssemblyDefaultContext.java    From ghidra with Apache License 2.0 4 votes vote down vote up
@Override
public void clearRegister(Register register) throws ContextChangeException {
	dbg.println("Clear " + register);
}
 
Example #18
Source File: AssemblyDefaultContext.java    From ghidra with Apache License 2.0 4 votes vote down vote up
@Override
public void setRegisterValue(RegisterValue value) throws ContextChangeException {
	dbg.println("Set " + value);
}
 
Example #19
Source File: AssemblyDefaultContext.java    From ghidra with Apache License 2.0 4 votes vote down vote up
@Override
public void setValue(Register register, BigInteger value) throws ContextChangeException {
	dbg.println("Set " + register + " to " + value);
}
 
Example #20
Source File: X86_32_ElfExtension.java    From ghidra with Apache License 2.0 4 votes vote down vote up
/**
 * Handle the case where GOT entry offset are computed based upon EBX.  
 * This implementation replaces the old "magic map" which had previously been used.
 * @param elfLoadHelper
 * @param monitor
 * @throws CancelledException
 */
private void processX86Plt(ElfLoadHelper elfLoadHelper, TaskMonitor monitor) throws CancelledException {
	
	// TODO: Does 64-bit have a similar mechanism?

	// TODO: Would be better to use only dynamic table entries since sections may be stripped -
	// the unresolved issue is to determine the length of the PLT area without a section
	
	ElfHeader elfHeader = elfLoadHelper.getElfHeader();
	ElfSectionHeader pltSection = elfHeader.getSection(ElfSectionHeaderConstants.dot_plt);
	if (pltSection == null || !pltSection.isExecutable()) {
		return;
	}
	
	ElfDynamicTable dynamicTable = elfHeader.getDynamicTable();
	if (dynamicTable == null || !dynamicTable.containsDynamicValue(ElfDynamicType.DT_PLTGOT)) {
		return; // avoid NotFoundException which causes issues for importer
	}
	
	Program program = elfLoadHelper.getProgram();
	Memory memory = program.getMemory();
	
	// MemoryBlock pltBlock = getBlockPLT(pltSection);
	MemoryBlock pltBlock = memory.getBlock(pltSection.getNameAsString());
	// TODO: This is a band-aid since there are many PLT implementations and this assumes only one.
	if (pltBlock == null || pltBlock.getSize() <= ElfConstants.PLT_ENTRY_SIZE) {
		return;
	}

	// Paint pltgot base over .plt section to allow thunks to be resolved during analysis
	Register ebxReg = program.getRegister("EBX");
	try {
		long pltgotOffset = elfHeader.adjustAddressForPrelink(dynamicTable.getDynamicValue(
				ElfDynamicType.DT_PLTGOT));
		pltgotOffset = elfLoadHelper.getDefaultAddress(pltgotOffset).getOffset(); // adjusted for image base
		RegisterValue pltgotValue = new RegisterValue(ebxReg, BigInteger.valueOf(pltgotOffset));
		program.getProgramContext().setRegisterValue(pltBlock.getStart(), pltBlock.getEnd(), pltgotValue);
	} catch (NotFoundException | ContextChangeException e) {
		throw new AssertException("unexpected", e);
	}

}
 
Example #21
Source File: ARM_ElfExtension.java    From ghidra with Apache License 2.0 4 votes vote down vote up
@Override
public Address evaluateElfSymbol(ElfLoadHelper elfLoadHelper, ElfSymbol elfSymbol,
		Address address, boolean isExternal) {

	if (isExternal) {
		return address;
	}

	Program program = elfLoadHelper.getProgram();

	String symName = elfSymbol.getNameAsString();

	try {
		Register tmodeRegister = program.getRegister("TMode");

		// ELF ARM - tags ARM code with $a and Thumb code with $t
		//
		if (tmodeRegister == null) {
			// Thumb Mode not supported by language
		}
		else if ("$t".equals(symName) || symName.startsWith("$t.")) {
			// is thumb mode
			program.getProgramContext().setValue(tmodeRegister, address, address,
				BigInteger.valueOf(1));
			elfLoadHelper.markAsCode(address);

			// do not retain $t symbols in program due to potential function/thunk naming interference
			elfLoadHelper.setElfSymbolAddress(elfSymbol, address);
			return null;
		}
		else if ("$a".equals(symName) || symName.startsWith("$a.")) {
			// is arm mode
			program.getProgramContext().setValue(tmodeRegister, address, address,
				BigInteger.valueOf(0));
			elfLoadHelper.markAsCode(address);

			// do not retain $a symbols in program due to potential function/thunk naming interference
			elfLoadHelper.setElfSymbolAddress(elfSymbol, address);
			return null;
		}
		else if ("$b".equals(symName)) {
			// don't do anything this is data
		}
		else if ("$d".equals(symName) || symName.startsWith("$d.")) {
			// is data, need to protect as data
			elfLoadHelper.createUndefinedData(address, (int) elfSymbol.getSize());

			// do not retain $d symbols in program due to excessive duplicate symbols
			elfLoadHelper.setElfSymbolAddress(elfSymbol, address);
			return null;
		}
		if (elfSymbol.getType() == ElfSymbol.STT_FUNC) {
			long symVal = address.getOffset();
			if ((symVal & 1) != 0 && tmodeRegister != null) {
				address = address.previous();
				program.getProgramContext().setValue(tmodeRegister, address, address,
					BigInteger.valueOf(1));
			}
		}
	}
	catch (ContextChangeException e) {
		// ignore since should not be instructions at time of import
	}
	return address;
}
 
Example #22
Source File: ProcessorContext.java    From ghidra with Apache License 2.0 2 votes vote down vote up
/**
 * Sets the value for a Register.
 * @param register the register to have its value set
 * @param value the value for the register (null is not permitted).
 * @throws ContextChangeException an illegal attempt to change context was made
 */
public void setValue(Register register, BigInteger value) throws ContextChangeException;
 
Example #23
Source File: ProcessorContext.java    From ghidra with Apache License 2.0 2 votes vote down vote up
/**
 * Sets the specified register value within this context.
 * @param value register value
 * @throws ContextChangeException an illegal attempt to change context was made
 */
public void setRegisterValue(RegisterValue value) throws ContextChangeException;
 
Example #24
Source File: ProcessorContext.java    From ghidra with Apache License 2.0 2 votes vote down vote up
/**
 * Clears the register within this context.
 * @param register register to be cleared.
 * @throws ContextChangeException an illegal attempt to change context was made
 */
public void clearRegister(Register register) throws ContextChangeException;