📄 tty.java
字号:
* Courtesy of Gordon Hirsch of SAS.
*/
void step(StringTokenizer t) throws Exception {
if (currentThread == null) {
out.println("Nothing suspended.");
return;
}
try {
if (t.hasMoreTokens()) {
String nt = t.nextToken().toLowerCase();
if (nt.equals("up")) {
currentThread.stepOut();
} else {
currentThread.step(true);
}
} else {
currentThread.step(true);
}
} catch (IllegalAccessError e) {
out.println("Current thread is not suspended.");
}
}
/* stepi
* step instruction.
* Courtesy of Gordon Hirsch of SAS.
*/
void stepi() throws Exception {
if (currentThread == null) {
out.println("Nothing suspended.");
return;
}
try {
currentThread.step(false);
} catch (IllegalAccessError e) {
out.println("Current thread is not suspended.");
}
}
void next() throws Exception {
if (currentThread == null) {
out.println("Nothing suspended.");
return;
}
try {
currentThread.next();
} catch (IllegalAccessError e) {
out.println("Current thread is not suspended.");
}
}
void kill(StringTokenizer t) throws Exception {
if (!t.hasMoreTokens()) {
out.println("Usage: kill <threadgroup name> or <thread id>");
return;
}
while (t.hasMoreTokens()) {
String idToken = t.nextToken();
int threadId;
try {
threadId = Integer.valueOf(idToken).intValue();
} catch (NumberFormatException e) {
threadId = 0;
}
RemoteThread thread = indexToThread(threadId);
if (thread != null) {
out.println("killing thread: " + thread.getName());
thread.stop();
return;
} else {
/* Check for threadgroup name, skipping "system". */
RemoteThreadGroup tglist[] = debugger.listThreadGroups(null);
tglist = debugger.listThreadGroups(tglist[0]);
for (int i = 0; i < tglist.length; i++) {
if (tglist[i].getName().equals(idToken)) {
out.println("killing threadgroup: " + idToken);
tglist[i].stop();
return;
}
}
out.println("\"" + idToken +
"\" is not a valid threadgroup or id.");
}
}
}
void catchException(StringTokenizer t) throws Exception {
if (!t.hasMoreTokens()) {
String exceptionList[] = debugger.getExceptionCatchList();
for (int i = 0; i < exceptionList.length; i++) {
out.print(" " + exceptionList[i]);
if ((i & 4) == 3 || (i == exceptionList.length - 1)) {
out.println();
}
}
} else {
String idClass = t.nextToken();
try {
RemoteClass cls = getClassFromToken(idClass);
cls.catchExceptions();
} catch (Exception e) {
out.println("Invalid exception class name: " + idClass);
}
}
}
void ignoreException(StringTokenizer t) throws Exception {
if (!t.hasMoreTokens()) {
String exceptionList[] = debugger.getExceptionCatchList();
for (int i = 0; i < exceptionList.length; i++) {
out.print(" " + exceptionList[i]);
if ((i & 4) == 3 || (i == exceptionList.length - 1)) {
out.println();
}
}
} else {
String idClass = t.nextToken();
try {
RemoteClass cls = getClassFromToken(idClass);
cls.ignoreExceptions();
} catch (Exception e) {
out.println("Invalid exception class name: " + idClass);
}
}
}
void up(StringTokenizer t) throws Exception {
if (currentThread == null) {
out.println("Current thread not set.");
return;
}
int nLevels = 1;
if (t.hasMoreTokens()) {
String idToken = t.nextToken();
int n;
try {
n = Integer.valueOf(idToken).intValue();
} catch (NumberFormatException e) {
n = 0;
}
if (n == 0) {
out.println("Usage: up [n frames]");
return;
}
nLevels = n;
}
try {
currentThread.up(nLevels);
} catch (IllegalAccessError e) {
out.println("Thread isn't suspended.");
} catch (ArrayIndexOutOfBoundsException e) {
out.println("End of stack.");
}
}
void down(StringTokenizer t) throws Exception {
if (currentThread == null) {
out.println("Current thread not set.");
return;
}
int nLevels = 1;
if (t.hasMoreTokens()) {
String idToken = t.nextToken();
int n;
try {
n = Integer.valueOf(idToken).intValue();
} catch (NumberFormatException e) {
n = 0;
}
if (n == 0) {
out.println("usage: down [n frames]");
return;
}
nLevels = n;
}
try {
currentThread.down(nLevels);
} catch (IllegalAccessError e) {
out.println("Thread isn't suspended.");
} catch (ArrayIndexOutOfBoundsException e) {
out.println("End of stack.");
}
}
void dumpStack(RemoteThread thread, boolean showPC) throws Exception {
RemoteStackFrame[] stack = thread.dumpStack();
if (stack.length == 0) {
out.println("Thread is not running (no stack).");
} else {
int nFrames = stack.length;
for (int i = thread.getCurrentFrameIndex(); i < nFrames; i++) {
out.print(" [" + (i + 1) + "] ");
out.print(stack[i].toString());
if (showPC) {
out.print(", pc = " + stack[i].getPC());
}
out.println();
}
}
}
void where(StringTokenizer t, boolean showPC) throws Exception {
if (!t.hasMoreTokens()) {
if (currentThread == null) {
out.println("No thread specified.");
return;
}
dumpStack(currentThread, showPC);
} else {
String token = t.nextToken();
if (token.toLowerCase().equals("all")) {
setDefaultThreadGroup();
RemoteThread list[] = currentThreadGroup.listThreads(true);
for (int i = 0; i < list.length; i++) {
out.println(list[i].getName() + ": ");
dumpStack(list[i], showPC);
}
} else {
int threadId = parseThreadId(token);
if (threadId == 0) {
return;
}
dumpStack(indexToThread(threadId), showPC);
}
}
}
void trace(String cmd, StringTokenizer t) throws Exception {
if (!t.hasMoreTokens()) {
out.println("(i)trace < \"on\" | \"off\" >");
return;
}
String v = t.nextToken();
boolean traceOn;
if (v.equals("on")) {
traceOn = true;
} else if (v.equals("off")) {
traceOn = false;
} else {
out.println("(i)trace < \"on\" | \"off\" >");
return;
}
if (cmd.equals("trace")) {
debugger.trace(traceOn);
} else {
debugger.itrace(traceOn);
}
}
void memory() throws Exception {
out.println("Free: " + debugger.freeMemory() + ", total: " +
debugger.totalMemory());
}
void gc() throws Exception {
RemoteObject[] save_list = new RemoteObject[2];
save_list[0] = currentThread;
save_list[1] = currentThreadGroup;
debugger.gc(save_list);
}
private RemoteClass getClassFromToken(String idToken) throws Exception {
RemoteObject obj;
if (idToken.startsWith("0x") ||
Character.isDigit(idToken.charAt(0))) {
/* It's an object id. */
int id;
try {
id = RemoteObject.fromHex(idToken);
} catch (NumberFormatException e) {
id = 0;
}
if (id == 0 || (obj = debugger.get(new Integer(id))) == null) {
throw new IllegalArgumentException();
} else if (!(obj instanceof RemoteClass)) {
throw new IllegalArgumentException();
}
} else {
/* It's a class */
obj = debugger.findClass(idToken);
if (obj == null) {
throw new IllegalArgumentException();
}
}
return (RemoteClass)obj;
}
void listBreakpoints() throws Exception {
String bkptList[] = debugger.listBreakpoints();
if (bkptList.length > 0) {
out.println("Current breakpoints set:");
for(int i = 0; i < bkptList.length; i++) {
out.println("\t" + bkptList[i]);
}
} else {
out.println("No breakpoints set.");
}
}
void stop(StringTokenizer t) throws Exception {
if (!t.hasMoreTokens()) {
listBreakpoints();
return;
}
String idClass = null;
try {
String modifier = t.nextToken();
boolean stopAt;
if (modifier.equals("at")) {
stopAt = true;
} else if (modifier.equals("in")) {
stopAt = false;
} else {
out.println("Usage: stop at <class>:<line_number> or");
out.println(" stop in <class>.<method_name>");
return;
}
if (modifier.equals("at")) {
idClass = t.nextToken(": \t\n\r");
RemoteClass cls = getClassFromToken(idClass);
String idLine = t.nextToken();
int lineno = Integer.valueOf(idLine).intValue();
String err = cls.setBreakpointLine(lineno);
if (err.length() > 0) {
out.println(err);
} else {
out.println("Breakpoint set at " + cls.getName() +
":" + lineno);
}
} else {
idClass = t.nextToken(": \t\n\r");
RemoteClass cls = null;
String idMethod = null;
try {
cls = getClassFromToken(idClass);
} catch (IllegalArgumentException e) {
// Try stripping method from class.method token.
int idot = idClass.lastIndexOf(".");
if (idot == -1) {
out.println("\"" + idClass +
"\" is not a valid id or class name.");
return;
}
idMethod = idClass.substring(idot + 1);
idClass = idClass.substring(0, idot);
cls = getClassFromToken(idClass);
}
if (idMethod == null) {
idMethod = t.nextToken();
}
RemoteField method;
try {
method = cls.getMethod(idMethod);
/*
* Prevent a breakpoint on overloaded method, since there
* is, currently, no way to choose among the overloads.
*/
RemoteField[] allMethods = cls.getMethods();
for (int i = 0; i < allMethods.length; i++) {
if (allMethods[i].getName().equals(idMethod)
&& (allMethods[i] != method)) {
out.println(cls.getName() + "." + idMethod
+ " is overloaded. Use the 'stop at' command to "
+ "set a breakpoint in one of the overloads");
return;
}
}
} catch (NoSuchMethodException nsme) {
out.println("Class " + cls.getName() +
" doesn't have a method " + idMethod);
return;
}
String err = cls.setBreakpointMethod(method);
if (err.length() > 0) {
out.println(err);
} else {
out.println("Breakpoint set in " + cls.getName() +
"." + idMethod);
}
}
} catch (NoSuchElementException e) {
out.println("Usage: stop at <class>:<line_number> or");
out.println(" stop in <class>.<method_name>");
} catch (NumberFormatException e) {
out.println("Invalid line number.");
} catch (IllegalArgumentException e) {
out.println("\"" + idClass +
"\" is not a valid id or class name.");
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -