GP-1288: more exception work

This commit is contained in:
d-millar 2021-09-21 21:25:56 +00:00
parent 2f1f78dc97
commit 4b98c30ff1
13 changed files with 200 additions and 113 deletions

View File

@ -384,14 +384,14 @@ public class DebugControlImpl1 implements DebugControlInternal {
public DebugExceptionFilterInformation getExceptionFilterParameters(int start, int[] codes,
int count) {
ULONG ulStart = new ULONG(start);
ULONG[] ulCodes = new ULONG[codes.length];
for (int i = 0; i < codes.length; i++) {
ulCodes[i] = new ULONG(codes[i]);
}
//ULONG[] ulCodes = new ULONG[codes.length];
//for (int i = 0; i < codes.length; i++) {
// ulCodes[i] = new ULONG(codes[i]);
//}
ULONG ulCount = new ULONG(count);
DEBUG_EXCEPTION_FILTER_PARAMETERS[] pParams = new DEBUG_EXCEPTION_FILTER_PARAMETERS[count];
COMUtils.checkRC(
jnaControl.GetExceptionFilterParameters(ulCount, ulCodes, ulStart, pParams));
jnaControl.GetExceptionFilterParameters(ulCount, null, ulStart, pParams));
return new DebugExceptionFilterInformation(count, pParams);
}

View File

@ -19,4 +19,6 @@ public interface DbgEventFilter {
String getName();
String getCmd();
}

View File

@ -19,4 +19,6 @@ public interface DbgExceptionFilter {
String getName();
String getArg();
}

View File

@ -18,32 +18,35 @@ package agent.dbgeng.manager.cmd;
import java.util.ArrayList;
import java.util.List;
import agent.dbgeng.dbgeng.DebugSpecificFilterInformation;
import agent.dbgeng.jna.dbgeng.DbgEngNative.DEBUG_SPECIFIC_FILTER_PARAMETERS;
import agent.dbgeng.dbgeng.DebugControl;
import agent.dbgeng.dbgeng.DebugFilterInformation;
import agent.dbgeng.manager.DbgEventFilter;
import agent.dbgeng.manager.impl.DbgEventFilterImpl;
import agent.dbgeng.manager.impl.DbgManagerImpl;
public class DbgListSpecificFiltersCommand
extends AbstractDbgCommand<List<DEBUG_SPECIFIC_FILTER_PARAMETERS>> {
private List<DEBUG_SPECIFIC_FILTER_PARAMETERS> result;
public class DbgListEventFiltersCommand
extends AbstractDbgCommand<List<DbgEventFilter>> {
private List<DbgEventFilter> result;
public DbgListSpecificFiltersCommand(DbgManagerImpl manager) {
public DbgListEventFiltersCommand(DbgManagerImpl manager) {
super(manager);
}
@Override
public List<DEBUG_SPECIFIC_FILTER_PARAMETERS> complete(DbgPendingCommand<?> pending) {
public List<DbgEventFilter> complete(DbgPendingCommand<?> pending) {
return result;
}
@Override
public void invoke() {
result = new ArrayList<>();
// TODO set parameters
DebugSpecificFilterInformation filterInfo =
manager.getControl().getSpecificFilterParameters(0, 0);
for (int i = 0; i < filterInfo.getNumberOfParameters(); i++) {
DEBUG_SPECIFIC_FILTER_PARAMETERS fi = filterInfo.getParameter(i);
result.add(fi);
DebugControl control = manager.getControl();
DebugFilterInformation info = control.getNumberEventFilters();
for (int i = 0; i < info.getNumberEvents(); i++) {
String text = control.getEventFilterText(i);
String cmd = control.getEventFilterCommand(i);
DbgEventFilterImpl f = new DbgEventFilterImpl(text, cmd);
result.add(f);
}
}
}

View File

@ -18,33 +18,33 @@ package agent.dbgeng.manager.cmd;
import java.util.ArrayList;
import java.util.List;
import agent.dbgeng.dbgeng.DebugExceptionFilterInformation;
import agent.dbgeng.jna.dbgeng.DbgEngNative.DEBUG_EXCEPTION_FILTER_PARAMETERS;
import agent.dbgeng.dbgeng.*;
import agent.dbgeng.manager.DbgExceptionFilter;
import agent.dbgeng.manager.impl.DbgManagerImpl;
public class DbgListExceptionFiltersCommand
extends AbstractDbgCommand<List<DEBUG_EXCEPTION_FILTER_PARAMETERS>> {
private List<DEBUG_EXCEPTION_FILTER_PARAMETERS> result;
extends AbstractDbgCommand<List<DbgExceptionFilter>> {
private List<DbgExceptionFilter> result;
public DbgListExceptionFiltersCommand(DbgManagerImpl manager) {
super(manager);
}
@Override
public List<DEBUG_EXCEPTION_FILTER_PARAMETERS> complete(DbgPendingCommand<?> pending) {
public List<DbgExceptionFilter> complete(DbgPendingCommand<?> pending) {
return result;
}
@Override
public void invoke() {
result = new ArrayList<>();
// TODO set up codes
int[] codes = new int[0];
DebugExceptionFilterInformation filterInfo =
manager.getControl().getExceptionFilterParameters(0, codes, 0);
for (int i = 0; i < filterInfo.getNumberOfParameters(); i++) {
DEBUG_EXCEPTION_FILTER_PARAMETERS fi = filterInfo.getParameter(i);
result.add(fi);
}
DebugControl control = manager.getControl();
DebugFilterInformation info = control.getNumberEventFilters();
int nEvents = info.getNumberEvents();
int nExcs = info.getNumberSpecificExceptions();
DebugSpecificFilterInformation spec = control.getSpecificFilterParameters(0, nEvents);
DebugExceptionFilterInformation exc =
control.getExceptionFilterParameters(nEvents, null, nExcs);
result = new ArrayList<>();
}
}

View File

@ -0,0 +1,39 @@
/* ###
* IP: GHIDRA
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package agent.dbgeng.manager.impl;
import agent.dbgeng.manager.DbgEventFilter;
public class DbgEventFilterImpl implements DbgEventFilter {
private final String text;
private final String cmd;
public DbgEventFilterImpl(String text, String cmd) {
this.text = text;
this.cmd = cmd;
}
@Override
public String getName() {
return text;
}
@Override
public String getCmd() {
return cmd;
}
}

View File

@ -0,0 +1,39 @@
/* ###
* IP: GHIDRA
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package agent.dbgeng.manager.impl;
import agent.dbgeng.manager.DbgExceptionFilter;
public class DbgExceptionFilterImpl implements DbgExceptionFilter {
private final String text;
private final String cmd;
public DbgExceptionFilterImpl(String text, String cmd) {
this.text = text;
this.cmd = cmd;
}
@Override
public String getName() {
return text;
}
@Override
public String getArg() {
return cmd;
}
}

View File

@ -1584,13 +1584,4 @@ public class DbgManagerImpl implements DbgManager {
public long getProcessCount() {
return processCount;
}
public CompletableFuture<Map<String, DbgEventFilter>> listEventFilters() {
return CompletableFuture.completedFuture(new HashMap<String, DbgEventFilter>());
}
public CompletableFuture<Map<String, DbgExceptionFilter>> listExceptionFilters() {
return CompletableFuture.completedFuture(new HashMap<String, DbgExceptionFilter>());
}
}

View File

@ -38,7 +38,7 @@ import ghidra.dbg.target.schema.TargetObjectSchemaInfo;
fixed = true),
@TargetAttributeType(
name = "Exceptions",
type = DbgModelTargetEventContainerImpl.class,
type = DbgModelTargetExceptionContainerImpl.class,
required = true,
fixed = true),
@TargetAttributeType(type = Void.class)

View File

@ -21,48 +21,63 @@ import java.util.concurrent.CompletableFuture;
import java.util.stream.Collectors;
import agent.dbgeng.manager.DbgEventFilter;
import agent.dbgeng.manager.cmd.DbgListEventFiltersCommand;
import agent.dbgeng.manager.impl.DbgManagerImpl;
import agent.dbgeng.model.iface2.*;
import ghidra.async.AsyncUtils;
import ghidra.dbg.target.TargetObject;
import ghidra.dbg.target.schema.*;
import ghidra.util.datastruct.WeakValueHashMap;
@TargetObjectSchemaInfo(
name = "EventContainer",
elements = { //
@TargetElementType(type = DbgModelTargetEvent.class) //
},
attributes = { //
@TargetAttributeType(type = Void.class) //
},
elements = {
@TargetElementType(type = DbgModelTargetEventImpl.class) },
attributes = {
@TargetAttributeType(type = Void.class) },
canonicalContainer = true)
public class DbgModelTargetEventContainerImpl extends DbgModelTargetObjectImpl
implements DbgModelTargetEventContainer {
protected final DbgModelTargetDebugContainer debug;
protected final Map<String, DbgModelTargetEventImpl> events =
new WeakValueHashMap<>();
public DbgModelTargetEventContainerImpl(DbgModelTargetDebugContainer debug) {
super(debug.getModel(), debug, "Events", "EventContainer");
}
public DbgModelTargetEvent getTargetEvent(DbgEventFilter info) {
DbgModelImpl impl = (DbgModelImpl) model;
TargetObject modelObject = impl.getModelObject(info);
if (modelObject != null) {
return (DbgModelTargetEvent) modelObject;
}
return new DbgModelTargetEventImpl(this, info);
this.debug = debug;
requestElements(true);
}
@Override
public CompletableFuture<Void> requestElements(boolean refresh) {
DbgManagerImpl manager = getManager();
return manager.listEventFilters().thenAccept(byName -> {
List<TargetObject> filters;
DbgModelTargetProcess targetProcess = getParentProcess();
if (!refresh || !targetProcess.getProcess().equals(getManager().getCurrentProcess())) {
return AsyncUtils.NIL;
}
return listEventFilters().thenAccept(byName -> {
List<TargetObject> eventObjs;
synchronized (this) {
filters = byName.values()
.stream()
.map(this::getTargetEvent)
.collect(Collectors.toList());
eventObjs = byName.stream().map(this::getTargetEvent).collect(Collectors.toList());
}
setElements(filters, Map.of(), "Refreshed");
setElements(eventObjs, Map.of(), "Refreshed");
});
}
public synchronized DbgModelTargetEvent getTargetEvent(DbgEventFilter filter) {
String id = filter.getName();
DbgModelTargetEventImpl event = events.get(id);
if (event != null && event.getFilter().getName().equals(id)) {
return event;
}
event = new DbgModelTargetEventImpl(this, filter);
events.put(filter.getName(), event);
return event;
}
public CompletableFuture<List<DbgEventFilter>> listEventFilters() {
DbgManagerImpl manager = getManager();
return manager.execute(new DbgListEventFiltersCommand(manager));
}
}

View File

@ -20,22 +20,12 @@ import agent.dbgeng.model.iface2.DbgModelTargetEvent;
import agent.dbgeng.model.iface2.DbgModelTargetEventContainer;
import ghidra.dbg.target.schema.*;
import ghidra.dbg.util.PathUtils;
import ghidra.program.model.address.Address;
@TargetObjectSchemaInfo(
name = "Module",
name = "Event",
elements = {
@TargetElementType(type = Void.class) },
attributes = {
@TargetAttributeType(
name = "Symbols",
type = DbgModelTargetSymbolContainerImpl.class,
required = true,
fixed = true),
@TargetAttributeType(name = "BaseAddress", type = Address.class),
@TargetAttributeType(name = "ImageName", type = String.class),
@TargetAttributeType(name = "TimeStamp", type = Integer.class),
@TargetAttributeType(name = "Len", type = String.class),
@TargetAttributeType(type = Void.class) })
public class DbgModelTargetEventImpl extends DbgModelTargetObjectImpl
implements DbgModelTargetEvent {

View File

@ -21,48 +21,64 @@ import java.util.concurrent.CompletableFuture;
import java.util.stream.Collectors;
import agent.dbgeng.manager.DbgExceptionFilter;
import agent.dbgeng.manager.cmd.DbgListExceptionFiltersCommand;
import agent.dbgeng.manager.impl.DbgManagerImpl;
import agent.dbgeng.model.iface2.*;
import ghidra.async.AsyncUtils;
import ghidra.dbg.target.TargetObject;
import ghidra.dbg.target.schema.*;
import ghidra.util.datastruct.WeakValueHashMap;
@TargetObjectSchemaInfo(
name = "ExceptionContainer",
elements = { //
@TargetElementType(type = DbgModelTargetEvent.class) //
},
attributes = { //
@TargetAttributeType(type = Void.class) //
},
elements = {
@TargetElementType(type = DbgModelTargetExceptionImpl.class) },
attributes = {
@TargetAttributeType(type = Void.class) },
canonicalContainer = true)
public class DbgModelTargetExceptionContainerImpl extends DbgModelTargetObjectImpl
implements DbgModelTargetEventContainer {
implements DbgModelTargetExceptionContainer {
protected final DbgModelTargetDebugContainer debug;
protected final Map<String, DbgModelTargetExceptionImpl> exceptions =
new WeakValueHashMap<>();
public DbgModelTargetExceptionContainerImpl(DbgModelTargetDebugContainer debug) {
super(debug.getModel(), debug, "Exceptions", "ExceptionContainer");
}
public DbgModelTargetException getTargetException(DbgExceptionFilter info) {
DbgModelImpl impl = (DbgModelImpl) model;
TargetObject modelObject = impl.getModelObject(info);
if (modelObject != null) {
return (DbgModelTargetException) modelObject;
}
return new DbgModelTargetExceptionImpl(this, info);
this.debug = debug;
requestElements(true);
}
@Override
public CompletableFuture<Void> requestElements(boolean refresh) {
DbgManagerImpl manager = getManager();
return manager.listExceptionFilters().thenAccept(byName -> {
List<TargetObject> filters;
DbgModelTargetProcess targetProcess = getParentProcess();
if (!refresh || !targetProcess.getProcess().equals(getManager().getCurrentProcess())) {
return AsyncUtils.NIL;
}
return listExceptionFilters().thenAccept(byName -> {
List<TargetObject> excObjs;
synchronized (this) {
filters = byName.values()
.stream()
.map(this::getTargetException)
.collect(Collectors.toList());
excObjs =
byName.stream().map(this::getTargetException).collect(Collectors.toList());
}
setElements(filters, Map.of(), "Refreshed");
setElements(excObjs, Map.of(), "Refreshed");
});
}
public synchronized DbgModelTargetException getTargetException(DbgExceptionFilter filter) {
String id = filter.getName();
DbgModelTargetExceptionImpl exc = exceptions.get(id);
if (exc != null && exc.getFilter().getName().equals(id)) {
return exc;
}
exc = new DbgModelTargetExceptionImpl(this, filter);
exceptions.put(filter.getName(), exc);
return exc;
}
public CompletableFuture<List<DbgExceptionFilter>> listExceptionFilters() {
DbgManagerImpl manager = getManager();
return manager.execute(new DbgListExceptionFiltersCommand(manager));
}
}

View File

@ -16,26 +16,16 @@
package agent.dbgeng.model.impl;
import agent.dbgeng.manager.DbgExceptionFilter;
import agent.dbgeng.model.iface2.DbgModelTargetEventContainer;
import agent.dbgeng.model.iface2.DbgModelTargetException;
import agent.dbgeng.model.iface2.DbgModelTargetExceptionContainer;
import ghidra.dbg.target.schema.*;
import ghidra.dbg.util.PathUtils;
import ghidra.program.model.address.Address;
@TargetObjectSchemaInfo(
name = "Module",
name = "Exception",
elements = {
@TargetElementType(type = Void.class) },
attributes = {
@TargetAttributeType(
name = "Symbols",
type = DbgModelTargetSymbolContainerImpl.class,
required = true,
fixed = true),
@TargetAttributeType(name = "BaseAddress", type = Address.class),
@TargetAttributeType(name = "ImageName", type = String.class),
@TargetAttributeType(name = "TimeStamp", type = Integer.class),
@TargetAttributeType(name = "Len", type = String.class),
@TargetAttributeType(type = Void.class) })
public class DbgModelTargetExceptionImpl extends DbgModelTargetObjectImpl
implements DbgModelTargetException {
@ -49,9 +39,9 @@ public class DbgModelTargetExceptionImpl extends DbgModelTargetObjectImpl
private DbgExceptionFilter filter;
public DbgModelTargetExceptionImpl(DbgModelTargetEventContainer events,
public DbgModelTargetExceptionImpl(DbgModelTargetExceptionContainer exceptions,
DbgExceptionFilter filter) {
super(events.getModel(), events, keyFilter(filter), "ExceptionFilter");
super(exceptions.getModel(), exceptions, keyFilter(filter), "ExceptionFilter");
this.getModel().addModelObject(filter, this);
this.filter = filter;