added some java doc and clean the code formatting

This commit is contained in:
Shu Lei
2007-11-08 19:09:40 +00:00
parent af51bf6f07
commit 4acaa11845
4 changed files with 162 additions and 117 deletions

View File

@@ -21,6 +21,10 @@
******************************************************************************/ ******************************************************************************/
package org.luaj.debug; package org.luaj.debug;
/**
* AbortException is thrown by DebugLuaState to abort the VM execution on request
* of the debugger client.
*/
public class AbortException extends RuntimeException { public class AbortException extends RuntimeException {
private static final long serialVersionUID = 8043724992294286647L; private static final long serialVersionUID = 8043724992294286647L;

View File

@@ -43,11 +43,11 @@ import org.luaj.debug.response.DebugResponseSimple;
import org.luaj.debug.response.DebugResponseVariables; import org.luaj.debug.response.DebugResponseVariables;
import org.luaj.vm.CallInfo; import org.luaj.vm.CallInfo;
import org.luaj.vm.LClosure; import org.luaj.vm.LClosure;
import org.luaj.vm.LPrototype;
import org.luaj.vm.LTable; import org.luaj.vm.LTable;
import org.luaj.vm.LValue; import org.luaj.vm.LValue;
import org.luaj.vm.LocVars; import org.luaj.vm.LocVars;
import org.luaj.vm.Lua; import org.luaj.vm.Lua;
import org.luaj.vm.LPrototype;
import org.luaj.vm.LuaState; import org.luaj.vm.LuaState;
@@ -66,13 +66,12 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
protected Hashtable breakpoints = new Hashtable(); protected Hashtable breakpoints = new Hashtable();
protected boolean exiting = false; protected boolean exiting = false;
protected boolean suspended = false; protected boolean suspended = false;
protected boolean bSuspendAtStart = false; protected boolean bSuspendOnStart = false;
protected int lastline = -1; protected int lastline = -1;
protected String lastSource; protected String lastSource;
protected DebugSupport debugSupport; protected DebugSupport debugSupport;
public DebugLuaState() { public DebugLuaState() {}
}
public void setDebugSupport(DebugSupport debugSupport) public void setDebugSupport(DebugSupport debugSupport)
throws IOException { throws IOException {
@@ -86,7 +85,7 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
} }
public void setSuspendAtStart(boolean bSuspendAtStart) { public void setSuspendAtStart(boolean bSuspendAtStart) {
this.bSuspendAtStart = bSuspendAtStart; this.bSuspendOnStart = bSuspendAtStart;
} }
protected void debugAssert(boolean b) { protected void debugAssert(boolean b) {
@@ -172,7 +171,7 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
} }
synchronized (this) { synchronized (this) {
while (bSuspendAtStart) { while (bSuspendOnStart) {
try { try {
this.wait(); this.wait();
} catch (InterruptedException e) { } catch (InterruptedException e) {
@@ -287,6 +286,11 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
return line; return line;
} }
/**
* Returns the current program counter for the given call frame.
* @param ci -- A call frame
* @return the current program counter for the given call frame.
*/
private int getCurrentPc(CallInfo ci) { private int getCurrentPc(CallInfo ci) {
int pc = (ci != calls[cc] ? ci.pc - 1 : ci.pc); int pc = (ci != calls[cc] ? ci.pc - 1 : ci.pc);
return pc; return pc;
@@ -308,7 +312,7 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
if (DebugRequestType.start == requestType) { if (DebugRequestType.start == requestType) {
DebugEvent event = new DebugEvent(DebugEventType.started); DebugEvent event = new DebugEvent(DebugEventType.started);
debugSupport.notifyDebugEvent(event); debugSupport.notifyDebugEvent(event);
setStarted(); cancelSuspendOnStart();
return DebugResponseSimple.SUCCESS; return DebugResponseSimple.SUCCESS;
} else if (DebugRequestType.exit == requestType) { } else if (DebugRequestType.exit == requestType) {
stop(); stop();
@@ -377,12 +381,17 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
} }
} }
protected void setStarted() { /**
* If the VM is suspended on start, this method resumes the execution.
*/
protected void cancelSuspendOnStart() {
synchronized (this) { synchronized (this) {
bSuspendAtStart = false; if (bSuspendOnStart) {
bSuspendOnStart = false;
this.notify(); this.notify();
} }
} }
}
/** /**
* resume the execution * resume the execution
@@ -395,6 +404,10 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
} }
} }
/**
* Stops the debugging communication with the debug client and terminate the
* VM execution.
*/
public void stop() { public void stop() {
if (this.debugSupport == null) { if (this.debugSupport == null) {
throw new IllegalStateException( throw new IllegalStateException(
@@ -427,8 +440,7 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
/** /**
* set breakpoint at line N * set breakpoint at line N
* *
* @param N * @param N -- the line to set the breakpoint at
* the line to set the breakpoint at
*/ */
public void setBreakpoint(String source, int lineNumber) { public void setBreakpoint(String source, int lineNumber) {
String fileName = DebugUtils.getSourceFileName(source); String fileName = DebugUtils.getSourceFileName(source);
@@ -501,6 +513,13 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
return result; return result;
} }
/**
* Check if the current LPrototype is lexically defined in the caller scope.
* @param p -- current LPrototype
* @param ci -- caller info
* @return true if the current LPrototype is lexically defined in the
* caller scope; false, otherwise.
*/
protected boolean isInScope(LPrototype p, CallInfo ci) { protected boolean isInScope(LPrototype p, CallInfo ci) {
LPrototype[] enclosingProtos = ci.closure.p.p; LPrototype[] enclosingProtos = ci.closure.p.p;
boolean bFound = false; boolean bFound = false;
@@ -534,9 +553,18 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
return result; return result;
} }
/**
* Debugging Utility. Dumps the variables for a given call frame.
* @param index Index of the call frame
*/
private void dumpStack(int index) { private void dumpStack(int index) {
if (index < 0 || index > cc) return;
CallInfo callInfo = calls[index]; CallInfo callInfo = calls[index];
LocVars[] localVariables = callInfo.closure.p.locvars; LPrototype prototype = callInfo.closure.p;
LocVars[] localVariables = prototype.locvars;
DebugUtils.println("Stack Frame: " + index + " [" + base + "," + top + "], # of localvars: " + localVariables.length + ", pc=" + callInfo.pc);
int pc = getCurrentPc(callInfo); int pc = getCurrentPc(callInfo);
for (int i = 0; i < localVariables.length; i++) { for (int i = 0; i < localVariables.length; i++) {
if (!isActiveVariable(pc, localVariables[i])) { if (!isActiveVariable(pc, localVariables[i])) {
@@ -545,8 +573,21 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
DebugUtils.println("localvars["+i+"]=" + localVariables[i].varname.toJavaString()); DebugUtils.println("localvars["+i+"]=" + localVariables[i].varname.toJavaString());
} }
} }
int base = callInfo.base;
int top = callInfo.top < callInfo.base ? callInfo.base+1 : callInfo.top;
for (int i = base; i < top; i++){
DebugUtils.println("stack[" + i + "]=" + stack[i]);
}
} }
/**
* Returns the name of the Nth variable in scope of the call info.
* @param callInfo Call info
* @param index Index of the variable
* @return the name of the Nth variable in scope of the call info. If the
* variable for the given index is not found, null is returned.
*/
private String getVariable(CallInfo callInfo, int index) { private String getVariable(CallInfo callInfo, int index) {
int count = -1; int count = -1;
LocVars[] localVariables = callInfo.closure.p.locvars; LocVars[] localVariables = callInfo.closure.p.locvars;
@@ -565,24 +606,30 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
return null; return null;
} }
/**
* Check if a variable is in scope.
* @param pc -- Current program counter.
* @param localVariable -- A local variable.
* @return true if the variable is active under the given program counter;
* false, otherwise.
*/
private boolean isActiveVariable(int pc, LocVars localVariable) { private boolean isActiveVariable(int pc, LocVars localVariable) {
return pc >= localVariable.startpc && pc <= localVariable.endpc; return pc >= localVariable.startpc && pc <= localVariable.endpc;
} }
/**
* Adds the active variables for the given call frame to the list of variables.
* @param variables -- the list of active variables.
* @param variablesSeen -- variables already seen so far
* @param index -- index of the call frame
*/
private void addVariables(Vector variables, Hashtable variablesSeen, int index) { private void addVariables(Vector variables, Hashtable variablesSeen, int index) {
CallInfo callInfo = calls[index]; CallInfo callInfo = calls[index];
LPrototype prototype = callInfo.closure.p;
int base = callInfo.base; int base = callInfo.base;
int top = callInfo.top < callInfo.base ? callInfo.base+1 : callInfo.top; int top = callInfo.top < callInfo.base ? callInfo.base+1 : callInfo.top;
if (DebugUtils.IS_DEBUG) { if (DebugUtils.IS_DEBUG) {
DebugUtils.println("Stack Frame: " + index + " [" + base + "," + top + "], # of localvars: " + prototype.locvars.length + ", pc=" + callInfo.pc); dumpStack(index);
for (int i = 0; i < prototype.locvars.length; i++) {
DebugUtils.println("localvars[" + i + "]: " + prototype.locvars[i].varname + "(" + prototype.locvars[i].startpc + "," + prototype.locvars[i].endpc + ")");
}
for (int i = base; i < top; i++){
DebugUtils.println("stack[" + i + "]=" + stack[i]);
}
} }
int selectedVariableCount = 0; int selectedVariableCount = 0;
@@ -649,7 +696,7 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
} }
/** /**
* step a single statement * step to the next statement
*/ */
public void stepInto() { public void stepInto() {
synchronized (this) { synchronized (this) {
@@ -660,7 +707,7 @@ public class DebugLuaState extends LuaState implements DebugRequestListener {
} }
/** /**
* return from the method call * return from the current method call
*/ */
public void stepReturn() { public void stepReturn() {
synchronized (this) { synchronized (this) {

View File

@@ -11,7 +11,10 @@ import org.luaj.debug.request.DebugRequest;
import org.luaj.debug.request.DebugRequestListener; import org.luaj.debug.request.DebugRequestListener;
import org.luaj.debug.response.DebugResponse; import org.luaj.debug.response.DebugResponse;
/**
* DebugSupport provides the network communication support for the debugger and
* debugee.
*/
public class DebugSupport implements DebugRequestListener, DebugEventListener { public class DebugSupport implements DebugRequestListener, DebugEventListener {
protected static final int UNKNOWN = 0; protected static final int UNKNOWN = 0;
protected static final int RUNNING = 1; protected static final int RUNNING = 1;
@@ -22,13 +25,11 @@ public class DebugSupport implements DebugRequestListener, DebugEventListener {
protected int eventPort; protected int eventPort;
protected Thread requestWatcherThread; protected Thread requestWatcherThread;
protected int state = UNKNOWN; protected int state = UNKNOWN;
protected DataInputStream requestReader; protected DataInputStream requestReader;
protected DataOutputStream requestWriter; protected DataOutputStream requestWriter;
protected DataOutputStream eventWriter; protected DataOutputStream eventWriter;
public DebugSupport(int requestPort, public DebugSupport(int requestPort, int eventPort) {
int eventPort) {
if (requestPort == -1) { if (requestPort == -1) {
throw new IllegalArgumentException("requestPort is invalid"); throw new IllegalArgumentException("requestPort is invalid");
} }
@@ -52,7 +53,8 @@ public class DebugSupport implements DebugRequestListener, DebugEventListener {
if (requestReader != null) { if (requestReader != null) {
try { try {
requestReader.close(); requestReader.close();
} catch (IOException e) {} } catch (IOException e) {
}
} }
if (requestWriter != null) { if (requestWriter != null) {
@@ -76,12 +78,10 @@ public class DebugSupport implements DebugRequestListener, DebugEventListener {
return (state == RUNNING || state == STOPPED); return (state == RUNNING || state == STOPPED);
} }
/* (non-Javadoc)
* @see lua.debug.j2se.DebugSupport#start()
*/
public synchronized void start() throws IOException { public synchronized void start() throws IOException {
if (this.vm == null) { if (this.vm == null) {
throw new IllegalStateException("DebugStackState is not set. Please call setDebugStackState first."); throw new IllegalStateException(
"DebugStackState is not set. Please call setDebugStackState first.");
} }
this.requestWatcherThread = new Thread(new Runnable() { this.requestWatcherThread = new Thread(new Runnable() {
@@ -93,16 +93,14 @@ public class DebugSupport implements DebugRequestListener, DebugEventListener {
this.requestWatcherThread.start(); this.requestWatcherThread.start();
this.state = RUNNING; this.state = RUNNING;
System.out.println("LuaJ debug server is started on ports: " + requestPort + ", " + eventPort); System.out.println("LuaJ debug server is started on ports: "
+ requestPort + ", " + eventPort);
} }
protected synchronized int getState() { protected synchronized int getState() {
return this.state; return this.state;
} }
/* (non-Javadoc)
* @see lua.debug.j2se.DebugSupport#stop()
*/
public synchronized void stop() { public synchronized void stop() {
if (DebugUtils.IS_DEBUG) if (DebugUtils.IS_DEBUG)
DebugUtils.println("stopping the debug support..."); DebugUtils.println("stopping the debug support...");
@@ -115,10 +113,11 @@ public class DebugSupport implements DebugRequestListener, DebugEventListener {
int size = requestReader.readInt(); int size = requestReader.readInt();
byte[] data = new byte[size]; byte[] data = new byte[size];
requestReader.readFully(data); requestReader.readFully(data);
DebugRequest request DebugRequest request = (DebugRequest) SerializationHelper
= (DebugRequest) SerializationHelper.deserialize(data); .deserialize(data);
if (DebugUtils.IS_DEBUG) if (DebugUtils.IS_DEBUG)
DebugUtils.println("SERVER receives request: " + request.toString()); DebugUtils.println("SERVER receives request: "
+ request.toString());
DebugResponse response = handleRequest(request); DebugResponse response = handleRequest(request);
data = SerializationHelper.serialize(response); data = SerializationHelper.serialize(response);
@@ -148,15 +147,12 @@ public class DebugSupport implements DebugRequestListener, DebugEventListener {
* client. The server can send events via this channel to notify the client * client. The server can send events via this channel to notify the client
* about debug events (see below) asynchronously. * about debug events (see below) asynchronously.
* *
* The following events can be fired: * The following events can be fired: 1. started -- the vm is started and
* 1. started -- the vm is started and ready to receive debugging requests * ready to receive debugging requests (guaranteed to be the first event
* (guaranteed to be the first event sent) * sent) 2. terminated -- the vm is terminated (guaranteed to be the last
* 2. terminated -- the vm is terminated (guaranteed to be the last event sent) * event sent) 3. suspended client|step|breakpoint N -- the vm is suspended
* 3. suspended client|step|breakpoint N * by client, due to a stepping request or the breakpoint at line N is hit
* -- the vm is suspended by client, due to a stepping request or * 4. resumed client|step -- the vm resumes execution by client or step
* the breakpoint at line N is hit
* 4. resumed client|step
* -- the vm resumes execution by client or step
* *
* @param event * @param event
*/ */
@@ -174,21 +170,19 @@ public class DebugSupport implements DebugRequestListener, DebugEventListener {
} }
} }
/* (non-Javadoc) /*
* @see lua.debug.DebugEventListener#notifyDebugEvent(lua.debug.DebugEvent) * (non-Javadoc)
*/ *
/* (non-Javadoc) * @see org.luaj.debug.event.DebugEventListener#notifyDebugEvent(org.luaj.debug.event.DebugEvent)
* @see lua.debug.j2se.DebugSupport#notifyDebugEvent(lua.debug.event.DebugEvent)
*/ */
public void notifyDebugEvent(DebugEvent event) { public void notifyDebugEvent(DebugEvent event) {
sendEvent(event); sendEvent(event);
} }
/* (non-Javadoc) /*
* @see lua.debug.DebugRequestListener#handleRequest(java.lang.String) * (non-Javadoc)
*/ *
/* (non-Javadoc) * @see org.luaj.debug.request.DebugRequestListener#handleRequest(org.luaj.debug.request.DebugRequest)
* @see lua.debug.j2se.DebugSupport#handleRequest(lua.debug.request.DebugRequest)
*/ */
public DebugResponse handleRequest(DebugRequest request) { public DebugResponse handleRequest(DebugRequest request) {
if (DebugUtils.IS_DEBUG) { if (DebugUtils.IS_DEBUG) {

View File

@@ -26,7 +26,7 @@ import org.luaj.vm.LoadState;
public class DebugUtils { public class DebugUtils {
public static final boolean IS_DEBUG = false; public static final boolean IS_DEBUG = (null != System.getProperty("TRACE"));
public static void println(String message) { public static void println(String message) {
if (IS_DEBUG) { if (IS_DEBUG) {