From 41c17c0ea23451715b4049f1dcfb12ef14c409a7 Mon Sep 17 00:00:00 2001 From: d-millar <33498836+d-millar@users.noreply.github.com> Date: Mon, 14 Mar 2022 12:59:29 -0400 Subject: [PATCH 1/4] GP-1822: modifying/adding addresses for navigation --- .../DbgModelTargetRegisterContainerImpl.java | 6 ++++- .../impl/DbgModelTargetRegisterImpl.java | 13 +++++++--- .../impl/DbgModelTargetStackFrameImpl.java | 18 +++++++------ .../model/impl/GdbModelTargetStackFrame.java | 6 ++++- .../GdbModelTargetStackFrameRegister.java | 7 ++++- .../impl/LldbModelTargetStackFrameImpl.java | 26 +++++++++++-------- ...LldbModelTargetStackFrameRegisterImpl.java | 8 +++++- 7 files changed, 58 insertions(+), 26 deletions(-) diff --git a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterContainerImpl.java b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterContainerImpl.java index f74a37d1b1..89ce388d5d 100644 --- a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterContainerImpl.java +++ b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterContainerImpl.java @@ -30,6 +30,7 @@ import ghidra.dbg.target.TargetRegisterBank; import ghidra.dbg.target.schema.*; import ghidra.dbg.target.schema.TargetObjectSchema.ResyncMode; import ghidra.dbg.util.ConversionUtils; +import ghidra.program.model.address.AddressSpace; @TargetObjectSchemaInfo( name = "RegisterContainer", @@ -104,6 +105,7 @@ public class DbgModelTargetRegisterContainerImpl extends DbgModelTargetObjectImp @Override public CompletableFuture> readRegistersNamed( Collection names) { + AddressSpace space = getModel().getAddressSpace("ram"); return model.gateFuture(thread.listRegisters().thenCompose(regs -> { if (regs.size() != registersByName.size() || getCachedElements().isEmpty()) { return requestElements(false); @@ -136,7 +138,8 @@ public class DbgModelTargetRegisterContainerImpl extends DbgModelTargetObjectImp if (value.longValue() != 0) { String newval = reg.getName() + " : " + value.toString(16); reg.changeAttributes(List.of(), Map.of( // - DISPLAY_ATTRIBUTE_NAME, newval // + DISPLAY_ATTRIBUTE_NAME, newval, // + "Address", space.getAddress(value.longValue()) // ), "Refreshed"); reg.setModified(!value.toString(16).equals(oldval)); } @@ -170,6 +173,7 @@ public class DbgModelTargetRegisterContainerImpl extends DbgModelTargetObjectImp })); } + @Override public Map getCachedRegisters() { return values; } diff --git a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterImpl.java b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterImpl.java index f131e301ce..a17e68d2ba 100644 --- a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterImpl.java +++ b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterImpl.java @@ -24,10 +24,17 @@ import agent.dbgeng.model.iface2.DbgModelTargetRegisterContainerAndBank; import ghidra.dbg.target.TargetRegister; import ghidra.dbg.target.schema.*; import ghidra.dbg.util.PathUtils; +import ghidra.program.model.address.Address; -@TargetObjectSchemaInfo(name = "RegisterDescriptor", elements = { - @TargetElementType(type = Void.class) }, attributes = { - @TargetAttributeType(name = TargetRegister.CONTAINER_ATTRIBUTE_NAME, type = DbgModelTargetRegisterContainerImpl.class), +@TargetObjectSchemaInfo( + name = "RegisterDescriptor", + elements = { + @TargetElementType(type = Void.class) }, + attributes = { + @TargetAttributeType( + name = TargetRegister.CONTAINER_ATTRIBUTE_NAME, + type = DbgModelTargetRegisterContainerImpl.class), + @TargetAttributeType(name = "Address", type = Address.class), @TargetAttributeType(type = Void.class) }) public class DbgModelTargetRegisterImpl extends DbgModelTargetObjectImpl implements DbgModelTargetRegister { diff --git a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetStackFrameImpl.java b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetStackFrameImpl.java index 49da5d6a28..0c189c45bd 100644 --- a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetStackFrameImpl.java +++ b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetStackFrameImpl.java @@ -27,6 +27,7 @@ import ghidra.dbg.target.TargetObject; import ghidra.dbg.target.schema.*; import ghidra.dbg.util.PathUtils; import ghidra.program.model.address.Address; +import ghidra.program.model.address.AddressSpace; @TargetObjectSchemaInfo( name = "StackFrame", @@ -41,16 +42,16 @@ import ghidra.program.model.address.Address; type = String.class), @TargetAttributeType( name = DbgModelTargetStackFrame.INST_OFFSET_ATTRIBUTE_NAME, - type = String.class), + type = Address.class), @TargetAttributeType( name = DbgModelTargetStackFrame.FRAME_OFFSET_ATTRIBUTE_NAME, - type = String.class), + type = Address.class), @TargetAttributeType( name = DbgModelTargetStackFrame.RETURN_OFFSET_ATTRIBUTE_NAME, - type = String.class), + type = Address.class), @TargetAttributeType( name = DbgModelTargetStackFrame.STACK_OFFSET_ATTRIBUTE_NAME, - type = String.class), + type = Address.class), @TargetAttributeType( name = DbgModelTargetStackFrame.VIRTUAL_ATTRIBUTE_NAME, type = Boolean.class), @@ -141,15 +142,16 @@ public class DbgModelTargetStackFrameImpl extends DbgModelTargetObjectImpl // TODO: module? "from" this.frame = frame; + AddressSpace space = getModel().getAddressSpace("ram"); changeAttributes(List.of(), List.of(), Map.of( // PC_ATTRIBUTE_NAME, pc, // DISPLAY_ATTRIBUTE_NAME, display = computeDisplay(frame), // FUNC_ATTRIBUTE_NAME, func, // FUNC_TABLE_ENTRY_ATTRIBUTE_NAME, Long.toHexString(funcTableEntry), // - INST_OFFSET_ATTRIBUTE_NAME, Long.toHexString(lval), // - FRAME_OFFSET_ATTRIBUTE_NAME, Long.toHexString(frameOffset), // - RETURN_OFFSET_ATTRIBUTE_NAME, Long.toHexString(returnOffset), // - STACK_OFFSET_ATTRIBUTE_NAME, Long.toHexString(stackOffset), // + INST_OFFSET_ATTRIBUTE_NAME, space.getAddress(lval), // + FRAME_OFFSET_ATTRIBUTE_NAME, space.getAddress(frameOffset), // + RETURN_OFFSET_ATTRIBUTE_NAME, space.getAddress(returnOffset), // + STACK_OFFSET_ATTRIBUTE_NAME, space.getAddress(stackOffset), // VIRTUAL_ATTRIBUTE_NAME, virtual // ), "Refreshed"); changeAttributes(List.of(), List.of(), Map.of( // diff --git a/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrame.java b/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrame.java index fd4ec70d47..46312423f1 100644 --- a/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrame.java +++ b/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrame.java @@ -28,12 +28,14 @@ import ghidra.dbg.target.schema.*; import ghidra.dbg.util.PathUtils; import ghidra.lifecycle.Internal; import ghidra.program.model.address.Address; +import ghidra.program.model.address.AddressSpace; @TargetObjectSchemaInfo( name = "StackFrame", elements = { @TargetElementType(type = Void.class) }, attributes = { + @TargetAttributeType(name = "Address", type = Address.class), @TargetAttributeType(type = Void.class) }) public class GdbModelTargetStackFrame extends DefaultTargetObject implements TargetStackFrame, GdbModelSelectableObject { @@ -99,12 +101,14 @@ public class GdbModelTargetStackFrame extends DefaultTargetObject @@ -82,10 +85,12 @@ public class GdbModelTargetStackFrameRegister boolean modified = (bigval.longValue() != 0 && value.equals(oldval)); String newval = getName() + " : " + value; + AddressSpace space = getModel().getAddressSpace("ram"); changeAttributes(List.of(), Map.of( // VALUE_ATTRIBUTE_NAME, value, // DISPLAY_ATTRIBUTE_NAME, newval, // - MODIFIED_ATTRIBUTE_NAME, modified // + MODIFIED_ATTRIBUTE_NAME, modified, // + "Address", space.getAddress(bigval.longValue()) // ), "Value Updated"); } diff --git a/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameImpl.java b/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameImpl.java index 21a9c3be78..44075ec6fa 100644 --- a/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameImpl.java +++ b/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameImpl.java @@ -31,6 +31,7 @@ import ghidra.dbg.target.schema.*; import ghidra.dbg.target.schema.TargetObjectSchema.ResyncMode; import ghidra.dbg.util.PathUtils; import ghidra.program.model.address.Address; +import ghidra.program.model.address.AddressSpace; @TargetObjectSchemaInfo( name = "StackFrame", @@ -50,19 +51,19 @@ import ghidra.program.model.address.Address; type = String.class), @TargetAttributeType( name = LldbModelTargetStackFrame.INST_OFFSET_ATTRIBUTE_NAME, - type = String.class), + type = Address.class), @TargetAttributeType( name = LldbModelTargetStackFrame.FRAME_OFFSET_ATTRIBUTE_NAME, - type = String.class), + type = Address.class), @TargetAttributeType( name = LldbModelTargetStackFrame.RETURN_OFFSET_ATTRIBUTE_NAME, - type = String.class), + type = Address.class), @TargetAttributeType( name = LldbModelTargetStackFrame.CALL_FRAME_OFFSET_ATTRIBUTE_NAME, - type = String.class), + type = Address.class), @TargetAttributeType( name = LldbModelTargetStackFrame.STACK_OFFSET_ATTRIBUTE_NAME, - type = String.class), + type = Address.class), @TargetAttributeType(type = Void.class) }) public class LldbModelTargetStackFrameImpl extends LldbModelTargetObjectImpl implements LldbModelTargetStackFrame { @@ -100,7 +101,7 @@ public class LldbModelTargetStackFrameImpl extends LldbModelTargetObjectImpl function = null; return; } - + this.registers = new LldbModelTargetStackFrameRegisterContainerImpl(this); this.function = new LldbModelTargetFunctionImpl(this, frame.GetFunction()); @@ -116,6 +117,7 @@ public class LldbModelTargetStackFrameImpl extends LldbModelTargetObjectImpl getManager().addEventsListener(this); } + @Override public String getDescription(int level) { SBStream stream = new SBStream(); SBFrame frame = (SBFrame) getModelObject(); @@ -127,7 +129,8 @@ public class LldbModelTargetStackFrameImpl extends LldbModelTargetObjectImpl if (frame.GetFunction() == null) { return String.format("#%d 0x%s", DebugClient.getId(frame), frame.GetPC().toString(16)); } - return String.format("#%d 0x%s in %s ()", DebugClient.getId(frame), frame.GetPC().toString(16), + return String.format("#%d 0x%s in %s ()", DebugClient.getId(frame), + frame.GetPC().toString(16), frame.GetDisplayFunctionName()); } @@ -163,14 +166,15 @@ public class LldbModelTargetStackFrameImpl extends LldbModelTargetObjectImpl this.stackOffset = frame.GetSP().longValue(); this.callFrameOffset = frame.GetCFA().longValue(); + AddressSpace space = getModel().getAddressSpace("ram"); changeAttributes(List.of(), List.of(), Map.of( // PC_ATTRIBUTE_NAME, pc, // DISPLAY_ATTRIBUTE_NAME, display = getDescription(0), //computeDisplay(frame), // FUNC_ATTRIBUTE_NAME, func, // - INST_OFFSET_ATTRIBUTE_NAME, Long.toHexString(lval), // - FRAME_OFFSET_ATTRIBUTE_NAME, Long.toHexString(frameOffset), // - STACK_OFFSET_ATTRIBUTE_NAME, Long.toHexString(stackOffset), // - CALL_FRAME_OFFSET_ATTRIBUTE_NAME, Long.toHexString(callFrameOffset) // + INST_OFFSET_ATTRIBUTE_NAME, space.getAddress(lval), // + FRAME_OFFSET_ATTRIBUTE_NAME, space.getAddress(frameOffset), // + STACK_OFFSET_ATTRIBUTE_NAME, space.getAddress(stackOffset), // + CALL_FRAME_OFFSET_ATTRIBUTE_NAME, space.getAddress(callFrameOffset) // ), "Refreshed"); } diff --git a/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameRegisterImpl.java b/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameRegisterImpl.java index 68cfb505e7..a431b8efd3 100644 --- a/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameRegisterImpl.java +++ b/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameRegisterImpl.java @@ -25,6 +25,7 @@ import agent.lldb.model.iface2.LldbModelTargetStackFrameRegister; import ghidra.dbg.target.schema.*; import ghidra.dbg.util.ConversionUtils; import ghidra.dbg.util.PathUtils; +import ghidra.program.model.address.AddressSpace; @TargetObjectSchemaInfo( name = "RegisterValue", @@ -60,6 +61,7 @@ public class LldbModelTargetStackFrameRegisterImpl ), "Initialized"); } + @Override public String getDescription(int level) { SBStream stream = new SBStream(); SBValue val = (SBValue) getModelObject(); @@ -89,6 +91,7 @@ public class LldbModelTargetStackFrameRegisterImpl return (SBValue) getModelObject(); } + @Override public byte[] getBytes() { String oldValue = value; value = getValue(); @@ -102,19 +105,22 @@ public class LldbModelTargetStackFrameRegisterImpl } BigInteger val = new BigInteger(value, 16); byte[] bytes = ConversionUtils.bigIntegerToBytes((int) getRegister().GetByteSize(), val); + AddressSpace space = getModel().getAddressSpace("ram"); changeAttributes(List.of(), Map.of( // VALUE_ATTRIBUTE_NAME, value // ), "Refreshed"); if (val.longValue() != 0) { String newval = getDescription(0); changeAttributes(List.of(), Map.of( // - DISPLAY_ATTRIBUTE_NAME, newval // + DISPLAY_ATTRIBUTE_NAME, newval, // + "Address", space.getAddress(val.longValue()) // ), "Refreshed"); setModified(!value.equals(oldValue)); } return bytes; } + @Override public String getDisplay() { return getValue() == null ? getName() : getName() + " : " + getValue(); } From 9ae62b1e63f5f86cd94afbc7ecac2fb20a3f8ad9 Mon Sep 17 00:00:00 2001 From: d-millar <33498836+d-millar@users.noreply.github.com> Date: Thu, 17 Mar 2022 18:51:05 -0400 Subject: [PATCH 2/4] GP-1822: backing out register changes, making Objects handle Strings --- .../DbgModelTargetRegisterContainerImpl.java | 5 +--- .../impl/DbgModelTargetRegisterImpl.java | 2 -- .../GdbModelTargetStackFrameRegister.java | 7 +----- ...LldbModelTargetStackFrameRegisterImpl.java | 5 +--- .../gui/objects/components/ObjectTable.java | 23 ++++++++++++++++++ .../gui/objects/components/ObjectTree.java | 24 +++++++++++++++++++ 6 files changed, 50 insertions(+), 16 deletions(-) diff --git a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterContainerImpl.java b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterContainerImpl.java index 89ce388d5d..122334b94f 100644 --- a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterContainerImpl.java +++ b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterContainerImpl.java @@ -30,7 +30,6 @@ import ghidra.dbg.target.TargetRegisterBank; import ghidra.dbg.target.schema.*; import ghidra.dbg.target.schema.TargetObjectSchema.ResyncMode; import ghidra.dbg.util.ConversionUtils; -import ghidra.program.model.address.AddressSpace; @TargetObjectSchemaInfo( name = "RegisterContainer", @@ -105,7 +104,6 @@ public class DbgModelTargetRegisterContainerImpl extends DbgModelTargetObjectImp @Override public CompletableFuture> readRegistersNamed( Collection names) { - AddressSpace space = getModel().getAddressSpace("ram"); return model.gateFuture(thread.listRegisters().thenCompose(regs -> { if (regs.size() != registersByName.size() || getCachedElements().isEmpty()) { return requestElements(false); @@ -138,8 +136,7 @@ public class DbgModelTargetRegisterContainerImpl extends DbgModelTargetObjectImp if (value.longValue() != 0) { String newval = reg.getName() + " : " + value.toString(16); reg.changeAttributes(List.of(), Map.of( // - DISPLAY_ATTRIBUTE_NAME, newval, // - "Address", space.getAddress(value.longValue()) // + DISPLAY_ATTRIBUTE_NAME, newval // ), "Refreshed"); reg.setModified(!value.toString(16).equals(oldval)); } diff --git a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterImpl.java b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterImpl.java index a17e68d2ba..5a1a16b772 100644 --- a/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterImpl.java +++ b/Ghidra/Debug/Debugger-agent-dbgeng/src/main/java/agent/dbgeng/model/impl/DbgModelTargetRegisterImpl.java @@ -24,7 +24,6 @@ import agent.dbgeng.model.iface2.DbgModelTargetRegisterContainerAndBank; import ghidra.dbg.target.TargetRegister; import ghidra.dbg.target.schema.*; import ghidra.dbg.util.PathUtils; -import ghidra.program.model.address.Address; @TargetObjectSchemaInfo( name = "RegisterDescriptor", @@ -34,7 +33,6 @@ import ghidra.program.model.address.Address; @TargetAttributeType( name = TargetRegister.CONTAINER_ATTRIBUTE_NAME, type = DbgModelTargetRegisterContainerImpl.class), - @TargetAttributeType(name = "Address", type = Address.class), @TargetAttributeType(type = Void.class) }) public class DbgModelTargetRegisterImpl extends DbgModelTargetObjectImpl implements DbgModelTargetRegister { diff --git a/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrameRegister.java b/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrameRegister.java index 07859b2aca..33add4b14a 100644 --- a/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrameRegister.java +++ b/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrameRegister.java @@ -25,15 +25,12 @@ import ghidra.dbg.target.TargetObject; import ghidra.dbg.target.TargetRegister; import ghidra.dbg.target.schema.*; import ghidra.dbg.util.PathUtils; -import ghidra.program.model.address.Address; -import ghidra.program.model.address.AddressSpace; @TargetObjectSchemaInfo( name = "RegisterValue", elements = { @TargetElementType(type = Void.class) }, attributes = { - @TargetAttributeType(name = "Address", type = Address.class), @TargetAttributeType(type = Void.class) }) public class GdbModelTargetStackFrameRegister extends DefaultTargetObject @@ -85,12 +82,10 @@ public class GdbModelTargetStackFrameRegister boolean modified = (bigval.longValue() != 0 && value.equals(oldval)); String newval = getName() + " : " + value; - AddressSpace space = getModel().getAddressSpace("ram"); changeAttributes(List.of(), Map.of( // VALUE_ATTRIBUTE_NAME, value, // DISPLAY_ATTRIBUTE_NAME, newval, // - MODIFIED_ATTRIBUTE_NAME, modified, // - "Address", space.getAddress(bigval.longValue()) // + MODIFIED_ATTRIBUTE_NAME, modified // ), "Value Updated"); } diff --git a/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameRegisterImpl.java b/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameRegisterImpl.java index a431b8efd3..8319004a3d 100644 --- a/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameRegisterImpl.java +++ b/Ghidra/Debug/Debugger-agent-lldb/src/main/java/agent/lldb/model/impl/LldbModelTargetStackFrameRegisterImpl.java @@ -25,7 +25,6 @@ import agent.lldb.model.iface2.LldbModelTargetStackFrameRegister; import ghidra.dbg.target.schema.*; import ghidra.dbg.util.ConversionUtils; import ghidra.dbg.util.PathUtils; -import ghidra.program.model.address.AddressSpace; @TargetObjectSchemaInfo( name = "RegisterValue", @@ -105,15 +104,13 @@ public class LldbModelTargetStackFrameRegisterImpl } BigInteger val = new BigInteger(value, 16); byte[] bytes = ConversionUtils.bigIntegerToBytes((int) getRegister().GetByteSize(), val); - AddressSpace space = getModel().getAddressSpace("ram"); changeAttributes(List.of(), Map.of( // VALUE_ATTRIBUTE_NAME, value // ), "Refreshed"); if (val.longValue() != 0) { String newval = getDescription(0); changeAttributes(List.of(), Map.of( // - DISPLAY_ATTRIBUTE_NAME, newval, // - "Address", space.getAddress(val.longValue()) // + DISPLAY_ATTRIBUTE_NAME, newval // ), "Refreshed"); setModified(!value.equals(oldValue)); } diff --git a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTable.java b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTable.java index d47cb32cd6..c778b0780b 100644 --- a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTable.java +++ b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTable.java @@ -296,6 +296,10 @@ public class ObjectTable implements ObjectPane { Long lval = (Long) value; addr = container.getTargetObject().getModel().getAddress("ram", lval); } + if (value instanceof String) { + String sval = (String) value; + addr = stringToAddress(container.getTargetObject(), addr, sval); + } if (modelService != null) { TraceRecorder recorder = modelService.getRecorderForSuccessor(container.getTargetObject()); @@ -306,4 +310,23 @@ public class ObjectTable implements ObjectPane { } } + private Address stringToAddress(TargetObject selectedObject, Address addr, String sval) { + try { + Long lval = Long.decode(sval); + addr = selectedObject.getModel().getAddress("ram", lval); + } + catch (NumberFormatException nfe) { + // IGNORE + } + if (addr == null) { + try { + Long lval = Long.decode("0x" + sval); + addr = selectedObject.getModel().getAddress("ram", lval); + } + catch (NumberFormatException nfe) { + // IGNORE + } + } + return addr; + } } diff --git a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java index f0043d763d..2ae758b57f 100644 --- a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java +++ b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java @@ -426,6 +426,10 @@ public class ObjectTree implements ObjectPane { Long lval = (Long) value; addr = selectedObject.getModel().getAddress("ram", lval); } + if (value instanceof String) { + String sval = (String) value; + addr = stringToAddress(selectedObject, addr, sval); + } if (modelService != null && addr != null) { TraceRecorder recorder = modelService.getRecorderForSuccessor(selectedObject); DebuggerMemoryMapper memoryMapper = recorder.getMemoryMapper(); @@ -434,4 +438,24 @@ public class ObjectTree implements ObjectPane { } } } + + private Address stringToAddress(TargetObject selectedObject, Address addr, String sval) { + try { + Long lval = Long.decode(sval); + addr = selectedObject.getModel().getAddress("ram", lval); + } + catch (NumberFormatException nfe) { + // IGNORE + } + if (addr == null) { + try { + Long lval = Long.decode("0x" + sval); + addr = selectedObject.getModel().getAddress("ram", lval); + } + catch (NumberFormatException nfe) { + // IGNORE + } + } + return addr; + } } From e3892f914feec34f79505f3ba4caf0a916d514b3 Mon Sep 17 00:00:00 2001 From: d-millar <33498836+d-millar@users.noreply.github.com> Date: Thu, 17 Mar 2022 19:36:50 -0400 Subject: [PATCH 3/4] GP-1822: consolidate navigate functions --- .../gui/objects/DebuggerObjectsProvider.java | 72 ++++++++++++++++++- .../gui/objects/components/ObjectTable.java | 64 ++--------------- .../gui/objects/components/ObjectTree.java | 68 ++---------------- 3 files changed, 81 insertions(+), 123 deletions(-) diff --git a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/DebuggerObjectsProvider.java b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/DebuggerObjectsProvider.java index 9cb56ca38d..8edf4ab1f0 100644 --- a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/DebuggerObjectsProvider.java +++ b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/DebuggerObjectsProvider.java @@ -45,6 +45,7 @@ import ghidra.app.plugin.core.debug.gui.DebuggerResources; import ghidra.app.plugin.core.debug.gui.DebuggerResources.*; import ghidra.app.plugin.core.debug.gui.objects.actions.*; import ghidra.app.plugin.core.debug.gui.objects.components.*; +import ghidra.app.plugin.core.debug.mapping.DebuggerMemoryMapper; import ghidra.app.services.*; import ghidra.async.*; import ghidra.dbg.*; @@ -63,8 +64,7 @@ import ghidra.framework.options.annotation.*; import ghidra.framework.plugintool.*; import ghidra.framework.plugintool.annotation.AutoConfigStateField; import ghidra.framework.plugintool.annotation.AutoServiceConsumed; -import ghidra.program.model.address.Address; -import ghidra.program.model.address.AddressRange; +import ghidra.program.model.address.*; import ghidra.program.model.listing.Program; import ghidra.trace.model.Trace; import ghidra.trace.model.thread.TraceThread; @@ -1252,6 +1252,21 @@ public class DebuggerObjectsProvider extends ComponentProviderAdapter .buildAndInstallLocal(this); groupTargetIndex++; + + new ActionBuilder("GoTo", plugin.getName()) + .keyBinding("G") + .toolBarGroup(DebuggerResources.GROUP_CONTROL, "X" + groupTargetIndex) + .popupMenuPath("&GoTo") + .popupMenuGroup(DebuggerResources.GROUP_CONTROL, "X" + groupTargetIndex) + .helpLocation(AbstractToggleAction.help(plugin)) + .enabledWhen(ctx -> isInstance(ctx, TargetObject.class)) + .popupWhen(ctx -> isInstance(ctx, TargetObject.class)) + .onAction(ctx -> performNavigate(ctx)) + .enabled(false) + .buildAndInstallLocal(this); + + groupTargetIndex++; + displayAsTreeAction = new DisplayAsTreeAction(tool, plugin.getName(), this); displayAsTableAction = new DisplayAsTableAction(tool, plugin.getName(), this); @@ -1545,6 +1560,16 @@ public class DebuggerObjectsProvider extends ComponentProviderAdapter }, "Couldn't configure one or more options"); } + public void performNavigate(ActionContext context) { + performAction(context, false, TargetObject.class, t -> { + if (t != null) { + Object value = t.getCachedAttribute(TargetObject.VALUE_ATTRIBUTE_NAME); + navigateToSelectedObject(t, value); + } + return AsyncUtils.NIL; + }, "Couldn't toggle"); + } + public void initiateConsole(ActionContext context) { performAction(context, false, TargetInterpreter.class, interpreter -> { getPlugin().showConsole(interpreter); @@ -1840,4 +1865,47 @@ public class DebuggerObjectsProvider extends ComponentProviderAdapter return listener.queue.in; } + public void navigateToSelectedObject(TargetObject selectedObject, Object value) { + if (listingService != null && value != null) { + Address addr = null; + if (value instanceof Address) { + addr = (Address) value; + } + if (value instanceof AddressRangeImpl) { + AddressRangeImpl range = (AddressRangeImpl) value; + addr = range.getMinAddress(); + } + if (value instanceof Long) { + Long lval = (Long) value; + addr = selectedObject.getModel().getAddress("ram", lval); + } + if (value instanceof String) { + String sval = (String) value; + addr = stringToAddress(selectedObject, addr, sval); + } + if (modelService != null && addr != null) { + TraceRecorder recorder = modelService.getRecorderForSuccessor(selectedObject); + DebuggerMemoryMapper memoryMapper = recorder.getMemoryMapper(); + Address traceAddr = memoryMapper.targetToTrace(addr); + listingService.goTo(traceAddr, true); + } + } + } + + private Address stringToAddress(TargetObject selectedObject, Address addr, String sval) { + Integer base = 16; + if (selectedObject instanceof TargetConfigurable) { + TargetConfigurable configurable = (TargetConfigurable) selectedObject; + base = + (Integer) configurable.getCachedAttribute(TargetConfigurable.BASE_ATTRIBUTE_NAME); + } + try { + Long lval = Long.parseLong(sval, base); + addr = selectedObject.getModel().getAddress("ram", lval); + } + catch (NumberFormatException nfe) { + // IGNORE + } + return addr; + } } diff --git a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTable.java b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTable.java index c778b0780b..0090f348c6 100644 --- a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTable.java +++ b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTable.java @@ -27,11 +27,7 @@ import docking.widgets.table.AbstractSortedTableModel; import docking.widgets.table.EnumeratedColumnTableModel; import ghidra.app.plugin.core.debug.gui.objects.DebuggerObjectsProvider; import ghidra.app.plugin.core.debug.gui.objects.ObjectContainer; -import ghidra.app.plugin.core.debug.mapping.DebuggerMemoryMapper; -import ghidra.app.services.*; import ghidra.dbg.target.TargetObject; -import ghidra.program.model.address.Address; -import ghidra.program.model.address.AddressRangeImpl; import ghidra.util.Swing; import ghidra.util.table.GhidraTable; import resources.ResourceManager; @@ -45,8 +41,6 @@ public class ObjectTable implements ObjectPane { private AbstractSortedTableModel model; private GhidraTable table; private JScrollPane component; - private DebuggerListingService listingService; - private DebuggerModelService modelService; public ObjectTable(ObjectContainer container, Class clazz, AbstractSortedTableModel model) { @@ -55,8 +49,6 @@ public class ObjectTable implements ObjectPane { this.container = container; this.clazz = clazz; this.model = model; - this.listingService = container.getProvider().getListingService(); - this.modelService = container.getProvider().getModelService(); table.getSelectionModel().addListSelectionListener(new ListSelectionListener() { @Override @@ -72,7 +64,11 @@ public class ObjectTable implements ObjectPane { @Override public void mouseClicked(MouseEvent e) { if (e.getClickCount() == 2) { - navigateToSelectedObject(); + int selectedRow = table.getSelectedRow(); + int selectedColumn = table.getSelectedColumn(); + Object value = table.getValueAt(selectedRow, selectedColumn); + container.getProvider() + .navigateToSelectedObject(container.getTargetObject(), value); } } }); @@ -279,54 +275,4 @@ public class ObjectTable implements ObjectPane { container.setTargetObject(targetObject); } - protected void navigateToSelectedObject() { - if (listingService != null) { - int selectedRow = table.getSelectedRow(); - int selectedColumn = table.getSelectedColumn(); - Object value = table.getValueAt(selectedRow, selectedColumn); - Address addr = null; - if (value instanceof Address) { - addr = (Address) value; - } - if (value instanceof AddressRangeImpl) { - AddressRangeImpl range = (AddressRangeImpl) value; - addr = range.getMinAddress(); - } - if (value instanceof Long) { - Long lval = (Long) value; - addr = container.getTargetObject().getModel().getAddress("ram", lval); - } - if (value instanceof String) { - String sval = (String) value; - addr = stringToAddress(container.getTargetObject(), addr, sval); - } - if (modelService != null) { - TraceRecorder recorder = - modelService.getRecorderForSuccessor(container.getTargetObject()); - DebuggerMemoryMapper memoryMapper = recorder.getMemoryMapper(); - Address traceAddr = memoryMapper.targetToTrace(addr); - listingService.goTo(traceAddr, true); - } - } - } - - private Address stringToAddress(TargetObject selectedObject, Address addr, String sval) { - try { - Long lval = Long.decode(sval); - addr = selectedObject.getModel().getAddress("ram", lval); - } - catch (NumberFormatException nfe) { - // IGNORE - } - if (addr == null) { - try { - Long lval = Long.decode("0x" + sval); - addr = selectedObject.getModel().getAddress("ram", lval); - } - catch (NumberFormatException nfe) { - // IGNORE - } - } - return addr; - } } diff --git a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java index 2ae758b57f..c1a75be66c 100644 --- a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java +++ b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java @@ -35,15 +35,11 @@ import docking.widgets.tree.support.GTreeSelectionEvent.EventOrigin; import docking.widgets.tree.support.GTreeSelectionListener; import ghidra.app.plugin.core.debug.gui.objects.DebuggerObjectsProvider; import ghidra.app.plugin.core.debug.gui.objects.ObjectContainer; -import ghidra.app.plugin.core.debug.mapping.DebuggerMemoryMapper; -import ghidra.app.services.*; import ghidra.async.AsyncUtils; import ghidra.async.TypeSpec; import ghidra.dbg.DebugModelConventions; import ghidra.dbg.target.TargetAccessConditioned; import ghidra.dbg.target.TargetObject; -import ghidra.program.model.address.Address; -import ghidra.program.model.address.AddressRangeImpl; import ghidra.util.*; import ghidra.util.task.SwingUpdateManager; import resources.ResourceManager; @@ -63,17 +59,11 @@ public class ObjectTree implements ObjectPane { private SwingUpdateManager restoreTreeStateManager = new SwingUpdateManager(this::restoreTreeState); - private DebuggerListingService listingService; - private DebuggerModelService modelService; - public ObjectTree(ObjectContainer container) { this.root = new ObjectNode(this, null, container); addToMap(null, container, root); this.tree = new GTree(root); - this.listingService = container.getProvider().getListingService(); - this.modelService = container.getProvider().getModelService(); - tree.addGTreeSelectionListener(new GTreeSelectionListener() { @Override public void valueChanged(GTreeSelectionEvent e) { @@ -165,7 +155,12 @@ public class ObjectTree implements ObjectPane { @Override public void mouseClicked(MouseEvent e) { if (e.getClickCount() == 2) { - navigateToSelectedObject(); + TargetObject selectedObject = getSelectedObject(); + if (selectedObject != null) { + Object value = + selectedObject.getCachedAttribute(TargetObject.VALUE_ATTRIBUTE_NAME); + container.getProvider().navigateToSelectedObject(selectedObject, value); + } } } }); @@ -407,55 +402,4 @@ public class ObjectTree implements ObjectPane { nodeMap.remove(path(node.getContainer())); } - protected void navigateToSelectedObject() { - if (listingService != null) { - TargetObject selectedObject = getSelectedObject(); - if (selectedObject == null) { - return; - } - Object value = selectedObject.getCachedAttribute(TargetObject.VALUE_ATTRIBUTE_NAME); - Address addr = null; - if (value instanceof Address) { - addr = (Address) value; - } - if (value instanceof AddressRangeImpl) { - AddressRangeImpl range = (AddressRangeImpl) value; - addr = range.getMinAddress(); - } - if (value instanceof Long) { - Long lval = (Long) value; - addr = selectedObject.getModel().getAddress("ram", lval); - } - if (value instanceof String) { - String sval = (String) value; - addr = stringToAddress(selectedObject, addr, sval); - } - if (modelService != null && addr != null) { - TraceRecorder recorder = modelService.getRecorderForSuccessor(selectedObject); - DebuggerMemoryMapper memoryMapper = recorder.getMemoryMapper(); - Address traceAddr = memoryMapper.targetToTrace(addr); - listingService.goTo(traceAddr, true); - } - } - } - - private Address stringToAddress(TargetObject selectedObject, Address addr, String sval) { - try { - Long lval = Long.decode(sval); - addr = selectedObject.getModel().getAddress("ram", lval); - } - catch (NumberFormatException nfe) { - // IGNORE - } - if (addr == null) { - try { - Long lval = Long.decode("0x" + sval); - addr = selectedObject.getModel().getAddress("ram", lval); - } - catch (NumberFormatException nfe) { - // IGNORE - } - } - return addr; - } } From c25f9192499721d2d6f814683223a6b3854a3821 Mon Sep 17 00:00:00 2001 From: d-millar <33498836+d-millar@users.noreply.github.com> Date: Fri, 18 Mar 2022 14:19:51 -0400 Subject: [PATCH 4/4] GP-1822: better range of objects/attributes --- .../model/impl/GdbModelTargetStackFrame.java | 5 +- .../gui/objects/DebuggerObjectsProvider.java | 72 ++++++++++++------- .../gui/objects/components/ObjectTree.java | 4 +- 3 files changed, 48 insertions(+), 33 deletions(-) diff --git a/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrame.java b/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrame.java index 46312423f1..c5e854a54d 100644 --- a/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrame.java +++ b/Ghidra/Debug/Debugger-agent-gdb/src/main/java/agent/gdb/model/impl/GdbModelTargetStackFrame.java @@ -28,14 +28,12 @@ import ghidra.dbg.target.schema.*; import ghidra.dbg.util.PathUtils; import ghidra.lifecycle.Internal; import ghidra.program.model.address.Address; -import ghidra.program.model.address.AddressSpace; @TargetObjectSchemaInfo( name = "StackFrame", elements = { @TargetElementType(type = Void.class) }, attributes = { - @TargetAttributeType(name = "Address", type = Address.class), @TargetAttributeType(type = Void.class) }) public class GdbModelTargetStackFrame extends DefaultTargetObject implements TargetStackFrame, GdbModelSelectableObject { @@ -101,14 +99,13 @@ public class GdbModelTargetStackFrame extends DefaultTargetObject { if (t != null) { - Object value = t.getCachedAttribute(TargetObject.VALUE_ATTRIBUTE_NAME); - navigateToSelectedObject(t, value); + navigateToSelectedObject(t, null); } return AsyncUtils.NIL; - }, "Couldn't toggle"); + }, "Couldn't navigate"); } public void initiateConsole(ActionContext context) { @@ -1865,30 +1864,51 @@ public class DebuggerObjectsProvider extends ComponentProviderAdapter return listener.queue.in; } - public void navigateToSelectedObject(TargetObject selectedObject, Object value) { - if (listingService != null && value != null) { - Address addr = null; - if (value instanceof Address) { - addr = (Address) value; - } - if (value instanceof AddressRangeImpl) { - AddressRangeImpl range = (AddressRangeImpl) value; - addr = range.getMinAddress(); - } - if (value instanceof Long) { - Long lval = (Long) value; - addr = selectedObject.getModel().getAddress("ram", lval); - } - if (value instanceof String) { - String sval = (String) value; - addr = stringToAddress(selectedObject, addr, sval); - } - if (modelService != null && addr != null) { - TraceRecorder recorder = modelService.getRecorderForSuccessor(selectedObject); - DebuggerMemoryMapper memoryMapper = recorder.getMemoryMapper(); - Address traceAddr = memoryMapper.targetToTrace(addr); - listingService.goTo(traceAddr, true); + public void navigateToSelectedObject(TargetObject object, Object value) { + if (listingService == null || listingService == null) { + return; + } + if (value == null) { + value = + object.getCachedAttribute(TargetBreakpointLocation.ADDRESS_ATTRIBUTE_NAME); + } + if (value == null) { + value = object.getCachedAttribute(TargetObject.PREFIX_INVISIBLE + "range"); + } + if (value == null) { + value = object.getCachedAttribute(TargetObject.VALUE_ATTRIBUTE_NAME); + } + if (value == null) { + return; + } + + Address addr = null; + if (value instanceof Address) { + addr = (Address) value; + } + else if (value instanceof AddressRangeImpl) { + AddressRangeImpl range = (AddressRangeImpl) value; + addr = range.getMinAddress(); + } + else if (value instanceof Long) { + Long lval = (Long) value; + addr = object.getModel().getAddress("ram", lval); + } + else if (value instanceof String) { + String sval = (String) value; + addr = stringToAddress(object, addr, sval); + } + if (addr != null) { + TraceRecorder recorder = modelService.getRecorderForSuccessor(object); + if (recorder == null) { + recorder = modelService.getRecorder(currentTrace); + if (recorder == null) { + return; + } } + DebuggerMemoryMapper memoryMapper = recorder.getMemoryMapper(); + Address traceAddr = memoryMapper.targetToTrace(addr); + listingService.goTo(traceAddr, true); } } diff --git a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java index c1a75be66c..ea33a88a76 100644 --- a/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java +++ b/Ghidra/Debug/Debugger/src/main/java/ghidra/app/plugin/core/debug/gui/objects/components/ObjectTree.java @@ -157,9 +157,7 @@ public class ObjectTree implements ObjectPane { if (e.getClickCount() == 2) { TargetObject selectedObject = getSelectedObject(); if (selectedObject != null) { - Object value = - selectedObject.getCachedAttribute(TargetObject.VALUE_ATTRIBUTE_NAME); - container.getProvider().navigateToSelectedObject(selectedObject, value); + container.getProvider().navigateToSelectedObject(selectedObject, null); } } }