new cooja plugin for monitoring memory areas, similar to the log listener.
This commit is contained in:
parent
cc5547a962
commit
68da954163
@ -271,4 +271,8 @@ public class MicaZMote extends AbstractEmulatedMote implements Mote {
|
||||
return "MicaZ " + getID();
|
||||
}
|
||||
|
||||
public MemoryMonitor createMemoryMonitor(MemoryEventHandler meh) {
|
||||
logger.fatal("Not implemented");
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
@ -57,16 +57,21 @@ import se.sics.cooja.motes.AbstractEmulatedMote;
|
||||
import se.sics.cooja.mspmote.interfaces.MspSerial;
|
||||
import se.sics.cooja.mspmote.plugins.CodeVisualizerSkin;
|
||||
import se.sics.cooja.mspmote.plugins.MspBreakpointContainer;
|
||||
import se.sics.cooja.plugins.BufferListener.BufferAccess;
|
||||
import se.sics.cooja.plugins.Visualizer;
|
||||
import se.sics.mspsim.cli.CommandHandler;
|
||||
import se.sics.mspsim.cli.LineListener;
|
||||
import se.sics.mspsim.cli.LineOutputStream;
|
||||
import se.sics.mspsim.core.CPUMonitor;
|
||||
import se.sics.mspsim.core.EmulationException;
|
||||
import se.sics.mspsim.core.MSP430;
|
||||
import se.sics.mspsim.core.MSP430Constants;
|
||||
import se.sics.mspsim.platform.GenericNode;
|
||||
import se.sics.mspsim.ui.JFrameWindowManager;
|
||||
import se.sics.mspsim.util.ComponentRegistry;
|
||||
import se.sics.mspsim.util.ConfigManager;
|
||||
import se.sics.mspsim.util.DebugInfo;
|
||||
import se.sics.mspsim.util.ELF;
|
||||
import se.sics.mspsim.util.MapEntry;
|
||||
import se.sics.mspsim.util.MapTable;
|
||||
|
||||
@ -484,7 +489,163 @@ public abstract class MspMote extends AbstractEmulatedMote implements Mote, Watc
|
||||
}
|
||||
|
||||
public String getExecutionDetails() {
|
||||
return executeCLICommand("stacktrace");
|
||||
return executeCLICommand("stacktrace");
|
||||
}
|
||||
|
||||
public String getPCString() {
|
||||
int pc = myCpu.reg[MSP430Constants.PC];
|
||||
ELF elf = (ELF)myCpu.getRegistry().getComponent(ELF.class);
|
||||
DebugInfo di = elf.getDebugInfo(pc);
|
||||
|
||||
/* Following code examples from MSPsim, DebugCommands.java */
|
||||
if (di == null) {
|
||||
di = elf.getDebugInfo(pc + 1);
|
||||
}
|
||||
if (di == null) {
|
||||
/* Return PC value */
|
||||
return String.format("*%02x", myCpu.reg[MSP430Constants.PC]);
|
||||
}
|
||||
|
||||
int lineNo = di.getLine();
|
||||
String file = di.getFile();
|
||||
file = file==null?"?":file;
|
||||
if (file.contains("/")) {
|
||||
/* strip path */
|
||||
file = file.substring(file.lastIndexOf('/')+1, file.length());
|
||||
}
|
||||
String function = di.getFunction();
|
||||
function = function==null?"?":function;
|
||||
if (function.contains(":")) {
|
||||
/* strip arguments */
|
||||
function = function.substring(0, function.lastIndexOf(':'));
|
||||
}
|
||||
return file + ":" + function + ":" + lineNo;
|
||||
|
||||
/*return executeCLICommand("line " + myCpu.reg[MSP430Constants.PC]);*/
|
||||
}
|
||||
|
||||
private class MultiCPUMonitor implements CPUMonitor {
|
||||
private ArrayList<CPUMonitor> ms = new ArrayList<CPUMonitor>();
|
||||
public void add(CPUMonitor m) {
|
||||
ms.add(m);
|
||||
}
|
||||
public void remove(CPUMonitor m) {
|
||||
ms.remove(m);
|
||||
}
|
||||
public void cpuAction(int type, int adr, int data) {
|
||||
for (CPUMonitor m: ms) {
|
||||
m.cpuAction(type, adr, data);
|
||||
}
|
||||
}
|
||||
}
|
||||
public MemoryMonitor createMemoryMonitor(final MemoryEventHandler meh) {
|
||||
return new MemoryMonitor() {
|
||||
private boolean started = false;
|
||||
private int address = -1;
|
||||
private int size = -1;
|
||||
private CPUMonitor myMonitor = null;
|
||||
private boolean isPointer = false;
|
||||
private MemoryMonitor pointedMemory = null;
|
||||
public boolean start(int address, int size) {
|
||||
if (started) {
|
||||
return started;
|
||||
}
|
||||
|
||||
final MemoryMonitor thisMonitor = this;
|
||||
myMonitor = new CPUMonitor() {
|
||||
public void cpuAction(int type, int adr, int data) {
|
||||
MemoryEventType t;
|
||||
if (type == CPUMonitor.MEMORY_WRITE) {
|
||||
t = MemoryEventType.WRITE;
|
||||
} else if (type == CPUMonitor.MEMORY_READ) {
|
||||
t = MemoryEventType.READ;
|
||||
} else {
|
||||
t = MemoryEventType.UNKNOWN;
|
||||
}
|
||||
|
||||
meh.event(thisMonitor, t, adr, data);
|
||||
}
|
||||
};
|
||||
|
||||
/* TODO Make sure no other part of Cooja overrides this! */
|
||||
|
||||
for (int a = address; a < address+size; a++) {
|
||||
if (myCpu.hasBreakPoint(a)) {
|
||||
if (myCpu.breakPoints[a] instanceof MultiCPUMonitor) {
|
||||
/* Extend */
|
||||
((MultiCPUMonitor)myCpu.breakPoints[a]).add(myMonitor);
|
||||
} else {
|
||||
/* Create multi and replace */
|
||||
CPUMonitor existingMonitor = myCpu.breakPoints[a];
|
||||
MultiCPUMonitor multiMonitor = new MultiCPUMonitor();
|
||||
multiMonitor.add(existingMonitor);
|
||||
multiMonitor.add(myMonitor);
|
||||
myCpu.clearBreakPoint(a);
|
||||
myCpu.setBreakPoint(a, multiMonitor);
|
||||
}
|
||||
} else {
|
||||
myCpu.setBreakPoint(a, myMonitor);
|
||||
}
|
||||
}
|
||||
|
||||
this.address = address;
|
||||
this.size = size;
|
||||
started = true;
|
||||
return started;
|
||||
}
|
||||
public void stop() {
|
||||
if (!started) {
|
||||
return;
|
||||
}
|
||||
started = false;
|
||||
|
||||
for (int a = address; a < address+size; a++) {
|
||||
if (!myCpu.hasBreakPoint(a)) {
|
||||
logger.fatal("Memory breakpoint was previously removed");
|
||||
return;
|
||||
}
|
||||
|
||||
if (myCpu.breakPoints[a] instanceof MultiCPUMonitor) {
|
||||
/* Remove */
|
||||
((MultiCPUMonitor)myCpu.breakPoints[a]).remove(myMonitor);
|
||||
} else {
|
||||
/* Clear */
|
||||
if (myCpu.breakPoints[a] != myMonitor) {
|
||||
logger.fatal("Memory breakpoint is not mine");
|
||||
return;
|
||||
}
|
||||
myCpu.clearBreakPoint(a);
|
||||
}
|
||||
}
|
||||
}
|
||||
public Mote getMote() {
|
||||
return MspMote.this;
|
||||
}
|
||||
public int getAddress() {
|
||||
return address;
|
||||
}
|
||||
public int getSize() {
|
||||
return size;
|
||||
}
|
||||
|
||||
public boolean isPointer() {
|
||||
return isPointer;
|
||||
}
|
||||
public void setPointer(boolean isPointer, MemoryMonitor pointedMemory) {
|
||||
this.isPointer = isPointer;
|
||||
this.pointedMemory = pointedMemory;
|
||||
}
|
||||
public MemoryMonitor getPointedMemory() {
|
||||
return pointedMemory;
|
||||
}
|
||||
|
||||
private BufferAccess lastBufferAccess = null;
|
||||
public void setLastBufferAccess(BufferAccess ba) {
|
||||
this.lastBufferAccess = ba;
|
||||
}
|
||||
public BufferAccess getLastBufferAccess() {
|
||||
return lastBufferAccess;
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
@ -3,7 +3,7 @@ se.sics.cooja.contikimote.interfaces.ContikiRadio.RADIO_TRANSMISSION_RATE_kbps =
|
||||
se.sics.cooja.contikimote.ContikiMoteType.MOTE_INTERFACES = se.sics.cooja.interfaces.Position se.sics.cooja.interfaces.Battery se.sics.cooja.contikimote.interfaces.ContikiVib se.sics.cooja.contikimote.interfaces.ContikiMoteID se.sics.cooja.contikimote.interfaces.ContikiRS232 se.sics.cooja.contikimote.interfaces.ContikiBeeper se.sics.cooja.interfaces.RimeAddress se.sics.cooja.contikimote.interfaces.ContikiIPAddress se.sics.cooja.contikimote.interfaces.ContikiRadio se.sics.cooja.contikimote.interfaces.ContikiButton se.sics.cooja.contikimote.interfaces.ContikiPIR se.sics.cooja.contikimote.interfaces.ContikiClock se.sics.cooja.contikimote.interfaces.ContikiLED se.sics.cooja.contikimote.interfaces.ContikiCFS se.sics.cooja.interfaces.Mote2MoteRelations se.sics.cooja.interfaces.MoteAttributes
|
||||
se.sics.cooja.contikimote.ContikiMoteType.C_SOURCES =
|
||||
se.sics.cooja.GUI.MOTETYPES = se.sics.cooja.motes.ImportAppMoteType se.sics.cooja.motes.DisturberMoteType se.sics.cooja.contikimote.ContikiMoteType
|
||||
se.sics.cooja.GUI.PLUGINS = se.sics.cooja.plugins.Visualizer se.sics.cooja.plugins.LogListener se.sics.cooja.plugins.TimeLine se.sics.cooja.plugins.MoteInformation se.sics.cooja.plugins.MoteInterfaceViewer se.sics.cooja.plugins.VariableWatcher se.sics.cooja.plugins.EventListener se.sics.cooja.plugins.RadioLogger se.sics.cooja.plugins.ScriptRunner se.sics.cooja.plugins.Notes
|
||||
se.sics.cooja.GUI.PLUGINS = se.sics.cooja.plugins.Visualizer se.sics.cooja.plugins.LogListener se.sics.cooja.plugins.TimeLine se.sics.cooja.plugins.MoteInformation se.sics.cooja.plugins.MoteInterfaceViewer se.sics.cooja.plugins.VariableWatcher se.sics.cooja.plugins.EventListener se.sics.cooja.plugins.RadioLogger se.sics.cooja.plugins.ScriptRunner se.sics.cooja.plugins.Notes se.sics.cooja.plugins.BufferListener
|
||||
se.sics.cooja.GUI.IP_DISTRIBUTORS = se.sics.cooja.ipdistributors.RandomIPDistributor se.sics.cooja.ipdistributors.SpatialIPDistributor se.sics.cooja.ipdistributors.IdIPDistributor
|
||||
se.sics.cooja.GUI.POSITIONERS = se.sics.cooja.positioners.RandomPositioner se.sics.cooja.positioners.LinearPositioner se.sics.cooja.positioners.EllipsePositioner se.sics.cooja.positioners.ManualPositioner
|
||||
se.sics.cooja.GUI.RADIOMEDIUMS = se.sics.cooja.radiomediums.UDGM se.sics.cooja.radiomediums.UDGMConstantLoss se.sics.cooja.radiomediums.DirectedGraphMedium se.sics.cooja.radiomediums.SilentRadioMedium
|
||||
|
@ -30,6 +30,9 @@
|
||||
package se.sics.cooja.motes;
|
||||
|
||||
import se.sics.cooja.Mote;
|
||||
import se.sics.cooja.plugins.BufferListener;
|
||||
import se.sics.cooja.plugins.BufferListener.BufferAccess;
|
||||
import se.sics.cooja.plugins.TimeLine;
|
||||
|
||||
public abstract class AbstractEmulatedMote extends AbstractWakeupMote implements Mote {
|
||||
|
||||
@ -42,8 +45,42 @@ public abstract class AbstractEmulatedMote extends AbstractWakeupMote implements
|
||||
|
||||
/**
|
||||
* @return Execution details, for instance a stack trace
|
||||
* @see TimeLine
|
||||
*/
|
||||
public String getExecutionDetails() {
|
||||
return null;
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return One-liner describing current PC, for instance source file and line.
|
||||
* May return null.
|
||||
*
|
||||
* @see BufferListener
|
||||
*/
|
||||
public String getPCString() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public interface MemoryMonitor {
|
||||
public boolean start(int address, int size);
|
||||
public void stop();
|
||||
public Mote getMote();
|
||||
public int getAddress();
|
||||
public int getSize();
|
||||
|
||||
public void setLastBufferAccess(BufferAccess ba);
|
||||
public BufferAccess getLastBufferAccess();
|
||||
|
||||
public boolean isPointer();
|
||||
public void setPointer(boolean isPointer, MemoryMonitor pointedMemory);
|
||||
public MemoryMonitor getPointedMemory();
|
||||
}
|
||||
|
||||
public enum MemoryEventType { READ, WRITE, UNKNOWN };
|
||||
public interface MemoryEventHandler {
|
||||
public void event(MemoryMonitor mm, MemoryEventType type, int adr, int data);
|
||||
}
|
||||
|
||||
public abstract MemoryMonitor createMemoryMonitor(MemoryEventHandler meh);
|
||||
|
||||
}
|
||||
|
1831
tools/cooja/java/se/sics/cooja/plugins/BufferListener.java
Normal file
1831
tools/cooja/java/se/sics/cooja/plugins/BufferListener.java
Normal file
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user