1 33 34 package edu.rice.cs.drjava.model.debug; 35 36 import edu.rice.cs.drjava.model.*; 37 import edu.rice.cs.plt.io.IOUtil; 38 import edu.rice.cs.util.Log; 39 40 import java.io.*; 41 42 46 public abstract class DebugTestCase extends GlobalModelTestCase { 47 48 52 54 protected volatile int _pendingNotifies = 0; 55 protected final Object _notifierLock = new Object (); 56 57 protected volatile JPDADebugger _debugger; 58 59 protected static final String DEBUG_CLASS = 60 "class DrJavaDebugClass {\n" + 61 " public void foo() {\n" + 62 " System.out.println(\"Foo Line 1\");\n" + 63 " bar();\n" + 64 " System.out.println(\"Foo Line 3\");\n" + 65 " }\n" + 66 " public void bar() {\n" + 67 " System.out.println(\"Bar Line 1\");\n" + 68 " System.out.println(\"Bar Line 2\");\n" + 69 " }\n" + 70 "}\n" + 71 "class DrJavaDebugClass2 {\n" + 72 " public void baz() {\n" + 73 " System.out.println(\"Baz Line 1\");\n" + 74 " new DrJavaDebugClass().bar();\n" + 75 " }\n" + 76 "}"; 77 78 protected static final String DEBUG_CLASS_WITH_PACKAGE = 79 "package a;\n" + 80 "public class DrJavaDebugClassWithPackage {\n" + 81 " public void foo() {\n" + 82 " System.out.println(\"foo line 1\");\n" + 83 " System.out.println(\"foo line 2\");\n" + 84 " }\n" + 85 "}"; 86 87 protected static final String SUSPEND_CLASS = 88 "class Suspender {\n" + 89 " public static void main(String[] args) {\n" + 90 " Thread t1 = new Thread(){\n" + 91 " public void run(){\n" + 92 " int a = 1;\n" + 93 " while(true);\n" + 94 " }\n" + 95 " };\n" + 96 " t1.start();\n" + 97 " }\n" + 98 "}"; 99 100 protected static final String MONKEY_CLASS = 101 "class Monkey {\n" + 102 " public static void main(String[] args) {\n" + 103 "\n" + 104 " Thread t = new Thread(){\n" + 105 " public void run(){\n" + 106 " try{\n" + 107 " Thread.sleep(1000);\n" + 108 " }\n" + 109 " catch(InterruptedException e){\n" + 110 " }\n" + 111 " System.out.println(\"I\'m a thread! Yeah!\");\n" + 112 " }\n" + 113 " };\n" + 114 " try{\n" + 115 " t.start();\n" + 116 " System.out.println(\"I just woke up. I\'m a big boy now.\");\n" + 117 " System.out.println(\"James likes bananas!\");\n" + 118 " System.out.println(\"Yes they do.\");\n" + 119 " }catch(Exception e){\n" + 120 " e.printStackTrace();\n" + 121 " }\n" + 122 " }\n" + 123 "}\n"; 124 125 protected static final String MONKEY_WITH_INNER_CLASS = 126 "class Monkey {\n" + 127 " static int foo = 6; \n" + 128 " class MonkeyInner { \n" + 129 " int innerFoo = 8;\n" + 130 " class MonkeyInnerInner { \n" + 131 " int innerInnerFoo = 10;\n" + 132 " public void innerMethod() { \n" + 133 " int innerMethodFoo;\n" + 134 " String nullString = null;\n" + 135 " innerMethodFoo = 12;\n" + 136 " foo++;\n" + 137 " innerFoo++;\n" + 138 " innerInnerFoo++;\n" + 139 " innerMethodFoo++;\n" + 140 " staticMethod();\n" + 141 " System.out.println(\"innerMethodFoo: \" + innerMethodFoo);\n" + 142 " }\n" + 143 " }\n" + 144 " }\n" + 145 " public void bar() {\n" + 146 " final MonkeyInner.MonkeyInnerInner mi = \n" + 147 " new MonkeyInner().new MonkeyInnerInner();\n" + 148 " mi.innerMethod();\n" + 149 " final int localVar = 99;\n" + 150 " new Thread() {\n" + 151 " public void run() {\n" + 152 " final int localVar = mi.innerInnerFoo;\n" + 153 " new Thread() {\n" + 154 " public void run() {\n" + 155 " new Thread() {\n" + 156 " public void run() {\n" + 157 " System.out.println(\"localVar = \" + localVar);\n" + 158 " }\n" + 159 " }.run();\n" + 160 " }\n" + 161 " }.run();\n" + 162 " }\n" + 163 " }.run();\n" + 164 " }\n" + 165 " public static void staticMethod() {\n" + 166 " int z = 3;\n" + 167 " }\n" + 168 "}\n"; 169 170 protected static final String INNER_CLASS_WITH_LOCAL_VARS = 171 "class InnerClassWithLocalVariables {\n" + 172 " public static void main(final String[] args) {\n" + 173 " final int numArgs = args.length;\n" + 174 " final int inlined = 0;\n" + 175 " new Runnable() {\n" + 176 " public void run() {\n" + 177 " System.out.println(\"numArgs: \" + numArgs);\n" + 178 " System.out.println(\"inlined: \" + inlined);\n" + 179 " System.out.println(\"args.length: \" + args.length);\n" + 180 " }\n" + 181 " }.run();\n" + 182 " }\n" + 183 "}\n"; 184 185 protected static final String CLASS_WITH_STATIC_FIELD = 186 "public class DrJavaDebugStaticField {\n" + 187 " public static int x = 0;\n" + 188 " public void bar() {\n" + 189 " System.out.println(\"x == \" + x);\n" + 190 " x++;\n" + 191 " }\n" + 192 " public static void main(String[] nu) {\n" + 193 " new Thread(\"stuff\") {\n" + 194 " public void run() {\n" + 195 " new DrJavaDebugStaticField().bar();\n" + 196 " }\n" + 197 " }.start();\n" + 198 " new DrJavaDebugStaticField().bar();\n" + 199 " }\n" + 200 "}"; 201 202 protected static final String MONKEY_STATIC_STUFF = 203 "class MonkeyStaticStuff {\n" + 204 " static int foo = 6;\n" + 205 " static class MonkeyInner {\n" + 206 " static int innerFoo = 8;\n" + 207 " static public class MonkeyTwoDeep {\n" + 208 " static int twoDeepFoo = 13;\n" + 209 " static class MonkeyThreeDeep {\n" + 210 " public static int threeDeepFoo = 18;\n" + 211 " public static void threeDeepMethod() {\n" + 212 " System.out.println(MonkeyStaticStuff.MonkeyInner.MonkeyTwoDeep.MonkeyThreeDeep.threeDeepFoo);\n" + 213 " System.out.println(MonkeyTwoDeep.twoDeepFoo);\n" + 214 " System.out.println(MonkeyStaticStuff.foo);\n" + 215 " System.out.println(MonkeyStaticStuff.MonkeyInner.innerFoo);\n" + 216 " System.out.println(MonkeyInner.MonkeyTwoDeep.twoDeepFoo);\n" + 217 " System.out.println(innerFoo);\n" + 218 " }\n" + 219 " }\n" + 220 " static int getNegativeTwo() { return -2; }\n" + 221 " }\n" + 222 " }\n" + 223 "}"; 224 225 protected static final String THREAD_DEATH_CLASS = 226 "class Jones {\n" + 227 " public static void threadShouldDie() {\n" + 228 " Thread cooper = new Thread() {\n" + 229 " public void run() {\n" + 230 " System.out.println(\"This thread should die.\");\n" + 231 " }\n" + 232 " };\n" + 233 " cooper.start();\n" + 234 " while(cooper.isAlive()) {}\n" + 235 " System.out.println(\"Thread died.\");\n" + 236 " }\n" + 237 "}"; 238 239 240 public void setUp() throws Exception { 241 _log.log("Setting up (DebugTestCase)" + this); 242 super.setUp(); 243 _debugger = (JPDADebugger) _model.getDebugger(); 244 assertNotNull("Debug Manager should not be null", _debugger); 245 } 246 247 248 public void tearDown() throws Exception { 249 _log.log("Tearing down (DebugTestCase)" + this); 250 _debugger = null; 251 super.tearDown(); 252 } 253 254 259 protected void _setPendingNotifies(int n) throws InterruptedException { 260 synchronized(_notifierLock) { 261 _log.log("Waiting for " + n + " notifications ..."); 262 _pendingNotifies = n; 263 } 264 } 265 266 267 protected void _notifyLock() { 268 synchronized(_notifierLock) { 269 _pendingNotifies--; 270 _log.log("notified; count = " + _pendingNotifies); 271 if (_pendingNotifies == 0) { 272 _log.log("Notify count reached 0 -- notifying!"); 273 _notifierLock.notifyAll(); } 275 if (_pendingNotifies < 0) fail("Notified too many times"); 276 } 277 } 278 279 285 protected OpenDefinitionsDocument _startupDebugger(String fileName, String classText) throws Exception { 286 File file = IOUtil.attemptCanonicalFile(new File(_tempDir, fileName)); 288 return _startupDebugger(file, classText); 289 } 290 291 297 protected OpenDefinitionsDocument _startupDebugger(File file, String classText) throws Exception { 298 _log.log("Compiling " + file); 300 OpenDefinitionsDocument doc = doCompile(classText, file); 301 _log.log("Staring debugger in " + this); 302 synchronized(_notifierLock) { 304 _setPendingNotifies(1); _debugger.startUp(); 306 while (_pendingNotifies > 0) _notifierLock.wait(); 307 } 308 _log.log("Finished starting debugger in " + this); 309 return doc; 310 } 311 312 313 protected void _shutdownWithoutSuspendedInteraction() throws Exception { 314 _log.log("Shutting down debugger in " + this + " without waiting"); 315 _model.getBreakpointManager().clearRegions(); 316 317 _log.log("Shutting down..."); 319 synchronized(_notifierLock) { 320 _setPendingNotifies(1); _debugger.shutdown(); 322 while (_pendingNotifies > 0) _notifierLock.wait(); 323 } 324 _log.log("Shut down."); 325 _log.log("Completed debugger shutdown for " + this); 326 } 327 328 329 protected void _shutdownAndWaitForInteractionEnded() throws Exception { 330 _log.log("Shutting down debugger in " + this + " with waiting"); 331 _model.getBreakpointManager().clearRegions(); 332 333 _log.log("Shutting down..."); 335 InterpretListener interpretListener = new InterpretListener() { 336 public void interpreterChanged(boolean inProgress) { 337 interpreterChangedCount++; 339 } 340 }; 341 _model.addListener(interpretListener); 342 synchronized(_notifierLock) { 343 _setPendingNotifies(2); _debugger.shutdown(); 345 while (_pendingNotifies > 0) _notifierLock.wait(); 346 } 347 interpretListener.assertInteractionEndCount(1); 348 interpretListener.assertInterpreterChangedCount(1); _model.removeListener(interpretListener); 350 351 _log.log("Shut down."); 352 _log.log("Completed debugger shutdown for " + this); 353 } 354 355 356 protected void _doSetCurrentThread(final DebugThreadData t) throws DebugException { 357 _debugger.setCurrentThread(t); 358 } 359 360 361 protected void _asyncStep(final int whatKind) { 362 new Thread ("asyncStep Thread") { 363 public void run() { 364 try { _debugger.step(whatKind); } 365 catch(DebugException dbe) { 366 dbe.printStackTrace(); 367 listenerFail("Debugger couldn't be resumed!\n" + dbe); 368 } 369 } 370 }.start(); 371 } 372 373 377 protected void _asyncResume() { 378 new Thread ("asyncResume Thread") { 379 public void run() { 380 try { _debugger.resume(); } 381 catch(DebugException dbe) { 382 dbe.printStackTrace(); 383 listenerFail("Debugger couldn't be resumed!\n" + dbe); 384 } 385 } 386 }.start(); 387 } 388 389 390 protected void _asyncDoSetCurrentThread(final DebugThreadData th) { 391 new Thread ("asyncDoSetCurrentThread Thread") { 392 public void run() { 393 try { _doSetCurrentThread(th); } 394 catch (DebugException dbe) { 395 dbe.printStackTrace(); 396 listenerFail("Couldn't set current thread in _asyncDoSetCurrentThread\n" + dbe); 397 } 398 } 399 }.start(); 400 } 401 402 403 protected class DebugTestListener implements DebugListener { 404 protected volatile int debuggerStartedCount = 0; 405 protected volatile int debuggerShutdownCount = 0; 406 protected volatile int threadLocationUpdatedCount = 0; 407 protected volatile int breakpointReachedCount = 0; 408 protected volatile int regionAddedCount = 0; 409 protected volatile int regionChangedCount = 0; 410 protected volatile int regionRemovedCount = 0; 411 protected volatile int watchSetCount = 0; 412 protected volatile int watchRemovedCount = 0; 413 protected volatile int stepRequestedCount = 0; 414 protected volatile int currThreadSuspendedCount = 0; 415 protected volatile int currThreadResumedCount = 0; 416 protected volatile int threadStartedCount = 0; 417 protected volatile int currThreadDiedCount = 0; 418 protected volatile int currThreadSetCount = 0; 419 protected volatile int nonCurrThreadDiedCount = 0; 420 421 public void assertDebuggerStartedCount(int i) { 422 assertEquals("number of times debuggerStarted fired", i, debuggerStartedCount); 423 } 424 425 public void assertDebuggerShutdownCount(int i) { 426 assertEquals("number of times debuggerShutdown fired", i, debuggerShutdownCount); 427 } 428 429 public void assertThreadLocationUpdatedCount(int i) { 430 assertEquals("number of times threadLocationUpdated fired", i, threadLocationUpdatedCount); 431 } 432 433 public void assertBreakpointReachedCount(int i) { 434 assertEquals("number of times breakpointReached fired", i, breakpointReachedCount); 435 } 436 437 public void assertRegionAddedCount(int i) { 438 assertEquals("number of times regionAdded fired", i, regionAddedCount); 439 } 440 441 public void assertRegionChangedCount(int i) { 442 assertEquals("number of times regionChanged fired", i, regionChangedCount); 443 } 444 445 public void assertRegionRemovedCount(int i) { 446 assertEquals("number of times regionRemoved fired", i, regionRemovedCount); 447 } 448 449 public void assertWatchSetCount(int i) { 450 assertEquals("number of times watchSet fired", i, watchSetCount); 451 } 452 453 public void assertWatchRemovedCount(int i) { 454 assertEquals("number of times watchRemoved fired", i, watchRemovedCount); 455 } 456 457 public void assertStepRequestedCount(int i) { 458 assertEquals("number of times stepRequested fired", i, stepRequestedCount); 459 } 460 461 public void assertStepFinishedCount(int i) { 462 assertEquals("number of times stepRequested fired", i, stepRequestedCount); 463 } 464 465 public void assertCurrThreadSuspendedCount(int i) { 466 assertEquals("number of times currThreadSuspended fired", i, currThreadSuspendedCount); 467 } 468 469 public void assertCurrThreadResumedCount(int i) { 470 assertEquals("number of times currThreadResumed fired", i, currThreadResumedCount); 471 } 472 473 public void assertCurrThreadSetCount(int i) { 474 assertEquals("number of times currThreadSet fired", i, currThreadSetCount); 475 } 476 477 public void assertThreadStartedCount(int i) { 478 assertEquals("number of times threadStarted fired", i,threadStartedCount); 479 } 480 481 public void assertCurrThreadDiedCount(int i) { 482 assertEquals("number of times currThreadDied fired", i, currThreadDiedCount); 483 } 484 485 public void assertNonCurrThreadDiedCount(int i) { 486 assertEquals("number of times nonCurrThreadDied fired", i, nonCurrThreadDiedCount); 487 } 488 489 490 public void debuggerStarted() { fail("debuggerStarted fired unexpectedly"); } 491 492 public void debuggerShutdown() { fail("debuggerShutdown fired unexpectedly"); } 493 494 public void threadLocationUpdated(OpenDefinitionsDocument doc, int lineNumber, boolean shouldHighlight) { 495 fail("threadLocationUpdated fired unexpectedly"); 496 } 497 498 public void breakpointReached(Breakpoint bp) { fail("breakpointReached fired unexpectedly"); } 499 500 public void regionAdded(Breakpoint bp, int index) { fail("regionAdded fired unexpectedly"); } 501 502 public void regionChanged(Breakpoint bp, int index) { fail("regionChanged fired unexpectedly"); } 503 504 public void regionRemoved(Breakpoint bp) { fail("regionRemoved fired unexpectedly"); } 505 506 public void watchSet(DebugWatchData w) { fail("watchSet fired unexpectedly"); } 507 508 public void watchRemoved(DebugWatchData w) { fail("watchRemoved fired unexpectedly"); } 509 510 public void stepRequested() { fail("stepRequested fired unexpectedly"); } 511 512 public void currThreadSuspended() { fail("currThreadSuspended fired unexpectedly"); } 513 514 public void currThreadResumed() { fail("currThreadResumed fired unexpectedly"); } 515 516 public void currThreadSet(DebugThreadData dtd) { fail("currThreadSet fired unexpectedly"); } 517 518 519 public void threadStarted() { threadStartedCount++; } 520 521 public void currThreadDied() { fail("currThreadDied fired unexpectedly"); } 522 523 524 public void nonCurrThreadDied() { nonCurrThreadDiedCount++; } 525 } 526 527 528 protected class DebugStartAndStopListener extends DebugTestListener { 529 public void debuggerStarted() { 530 synchronized(_notifierLock) { 532 debuggerStartedCount++; 533 _log.log("debuggerStarted " + debuggerStartedCount); 534 _notifyLock(); 535 } 536 } 537 public void debuggerShutdown() { 538 synchronized(_notifierLock) { 540 debuggerShutdownCount++; 541 _log.log("debuggerShutdown " + debuggerShutdownCount); 542 _notifyLock(); 543 } 544 } 545 } 546 547 548 protected class BreakpointTestListener extends DebugStartAndStopListener { 549 public BreakpointTestListener() { } 550 public void breakpointReached(Breakpoint bp) { 551 synchronized(_notifierLock) { 553 breakpointReachedCount++; 554 _log.log("breakpointReached " + breakpointReachedCount); 555 _notifyLock(); 556 } 557 } 558 public void regionAdded(Breakpoint bp, int index) { 559 regionAddedCount++; 561 } 562 public void regionRemoved(Breakpoint bp) { 563 regionRemovedCount++; 565 _log.log("regionRemoved " + regionRemovedCount); 566 } 567 568 public void currThreadSuspended() { 569 synchronized(_notifierLock) { 571 currThreadSuspendedCount++; 572 _log.log("threadSuspended " + currThreadSuspendedCount); 573 _notifyLock(); 574 } 575 } 576 public void currThreadResumed() { 577 currThreadResumedCount++; 579 _log.log("threadResumed " + currThreadResumedCount); 580 } 581 public void currThreadSet(DebugThreadData dtd) { 582 currThreadSetCount++; 584 _log.log("threadSet " + currThreadSetCount); 585 } 586 public void currThreadDied() { 587 synchronized(_notifierLock) { 589 currThreadDiedCount++; 590 _log.log("currThreadDied " + currThreadDiedCount); 591 _notifyLock(); 592 } 593 } 594 public void threadLocationUpdated(OpenDefinitionsDocument doc, int lineNumber, boolean shouldHighlight) { 595 synchronized(_notifierLock) { 597 threadLocationUpdatedCount++; 598 _log.log("threadUpdated " + threadLocationUpdatedCount); 599 _notifyLock(); 600 } 601 } 602 public void watchSet(DebugWatchData w) { 603 watchSetCount++; 605 _log.log("watchSet " + watchSetCount); 606 } 607 public void watchRemoved(DebugWatchData w) { 608 watchRemovedCount++; 610 _log.log("watchRemoved " + watchRemovedCount); 611 } 612 } 613 614 615 protected class StepTestListener extends BreakpointTestListener { 616 public void stepRequested() { 617 stepRequestedCount++; 619 _log.log("stepRequested " + stepRequestedCount); 620 } 621 } 622 623 625 protected class InterpretListener extends TestListener { 626 public void interactionStarted() { 627 synchronized(_notifierLock) { 628 interactionStartCount++; 629 _log.log("interactionStarted " + interactionStartCount); 630 _notifyLock(); 631 } 632 } 633 public void interactionEnded() { 634 synchronized(_notifierLock) { 635 interactionEndCount++; 636 _log.log("interactionEnded " + interactionEndCount); 637 _notifyLock(); 638 } 639 } 640 641 public void interpreterChanged(boolean inProgress) { 642 synchronized(_notifierLock) { 643 interpreterChangedCount++; 644 _log.log("interpreterChanged " + interpreterChangedCount); 645 _notifyLock(); 646 } 647 } 648 } 649 } | Popular Tags |