1 /* 2 * Copyright (c) 2001, 2015, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 */ 23 24 /** 25 * @test 26 * @bug 4407397 27 * @summary Test the requesting of exception events 28 * 29 * @author Robert Field 30 * 31 * @key intermittent 32 * @modules jdk.jdi 33 * @run build TestScaffold VMConnection 34 * @run compile -g ExceptionEvents.java 35 * 36 * @run driver ExceptionEvents N A StackOverflowCaughtTarg java.lang.Exception 37 * @run driver ExceptionEvents C A StackOverflowCaughtTarg null 38 * @run driver ExceptionEvents C A StackOverflowCaughtTarg java.lang.Error 39 * @run driver ExceptionEvents C A StackOverflowCaughtTarg java.lang.StackOverflowError 40 * @run driver ExceptionEvents N A StackOverflowCaughtTarg java.lang.NullPointerException 41 42 * @run driver ExceptionEvents N T StackOverflowCaughtTarg java.lang.Exception 43 * @run driver ExceptionEvents C T StackOverflowCaughtTarg null 44 * @run driver ExceptionEvents C T StackOverflowCaughtTarg java.lang.Error 45 * @run driver ExceptionEvents C T StackOverflowCaughtTarg java.lang.StackOverflowError 46 * @run driver ExceptionEvents N T StackOverflowCaughtTarg java.lang.NullPointerException 47 48 * @run driver ExceptionEvents N N StackOverflowCaughtTarg java.lang.Exception 49 * @run driver ExceptionEvents C N StackOverflowCaughtTarg null 50 * @run driver ExceptionEvents C N StackOverflowCaughtTarg java.lang.Error 51 * @run driver ExceptionEvents C N StackOverflowCaughtTarg java.lang.StackOverflowError 52 * @run driver ExceptionEvents N N StackOverflowCaughtTarg java.lang.NullPointerException 53 54 * @run driver ExceptionEvents N A StackOverflowUncaughtTarg java.lang.Exception 55 * @run driver ExceptionEvents U A StackOverflowUncaughtTarg null 56 * @run driver ExceptionEvents U A StackOverflowUncaughtTarg java.lang.Error 57 * @run driver ExceptionEvents U A StackOverflowUncaughtTarg java.lang.StackOverflowError 58 * @run driver ExceptionEvents N A StackOverflowUncaughtTarg java.lang.NullPointerException 59 60 * @run driver ExceptionEvents N T StackOverflowUncaughtTarg java.lang.NullPointerException 61 * @run driver ExceptionEvents N N StackOverflowUncaughtTarg java.lang.NullPointerException 62 63 */ 64 import com.sun.jdi.*; 65 import com.sun.jdi.event.*; 66 import com.sun.jdi.request.*; 67 import java.util.*; 68 69 class StackOverflowCaughtTarg { 70 public static void main(String[] args) { 71 try { 72 throw new StackOverflowError(); 73 } catch (Throwable exc) { 74 // ignore 75 } 76 } 77 } 78 79 class StackOverflowUncaughtTarg { 80 public static void main(String[] args) { 81 thrower(); 82 } 83 static void thrower() { 84 throw new StackOverflowError(); 85 } 86 } 87 88 class StackOverflowIndirectTarg { 89 public static void main(String[] args) { 90 try { 91 thrower(); 92 } catch (Throwable exc) { 93 System.out.println("Got exception: " + exc); 94 } 95 } 96 static void thrower() { 97 throw new StackOverflowError(); 98 } 99 } 100 101 public class ExceptionEvents extends TestScaffold { 102 static int failureCount = 0; 103 static StringBuffer tooManySummary = new StringBuffer(); 104 static StringBuffer notSentSummary = new StringBuffer(); 105 static StringBuffer unexpectedSummary = new StringBuffer(); 106 static int globalSuspendPolicy = -1; 107 static String[] flags; 108 109 final String target; 110 final String exceptionName; 111 final boolean caught; 112 final boolean uncaught; 113 final int suspendPolicy; 114 115 int eventCount = 0; 116 ExceptionRequest request; 117 118 ExceptionEvents(String target, 119 String exceptionName, 120 boolean caught, boolean uncaught, 121 int suspendPolicy) { 122 super(flags); 123 this.target = target; 124 this.exceptionName = exceptionName; 125 this.caught = caught; 126 this.uncaught = uncaught; 127 this.suspendPolicy = suspendPolicy; 128 } 129 130 static void everything() throws Exception { 131 goNeither("StackOverflowCaughtTarg", "java.lang.Exception"); 132 goCaught("StackOverflowCaughtTarg", null); 133 goCaught("StackOverflowCaughtTarg", "java.lang.Error"); 134 goCaught("StackOverflowCaughtTarg", "java.lang.StackOverflowError"); 135 goNeither("StackOverflowCaughtTarg", "java.lang.NullPointerException"); 136 137 goNeither("StackOverflowUncaughtTarg", "java.lang.Exception"); 138 goUncaught("StackOverflowUncaughtTarg", null); 139 goUncaught("StackOverflowUncaughtTarg", "java.lang.Error"); 140 goUncaught("StackOverflowUncaughtTarg", "java.lang.StackOverflowError"); 141 goNeither("StackOverflowUncaughtTarg", "java.lang.NullPointerException"); 142 } 143 144 static void usage() throws Exception { 145 System.err.println("Use either with no arguments or"); 146 System.err.println(" c|u|n a|t|n <TargetClass> <Exception>|null"); 147 System.err.println("or for verbose folk"); 148 System.err.println(" caught|uncaught|neither all|thread|none <TargetClass> <Exception>|null"); 149 throw new IllegalArgumentException("see usage"); 150 } 151 152 public static void main(String[] args) throws Exception { 153 StringBuffer testName = new StringBuffer("ExceptionEvents("); 154 List flagList = new ArrayList(); 155 List argList = new ArrayList(); 156 157 for (int i = 0; i < args.length; ++i) { 158 String arg = args[i]; 159 if (arg.startsWith("-")) { 160 flagList.add(arg); 161 } else { 162 argList.add(arg); 163 } 164 } 165 flags = (String[])flagList.toArray(new String[0]); 166 args = (String[])argList.toArray(new String[0]); 167 if (args.length == 0) { 168 everything(); 169 testName.append("Full Test"); 170 } else if (args.length == 4) { 171 switch (args[1].toLowerCase().charAt(0)) { 172 case 'a': 173 globalSuspendPolicy = EventRequest.SUSPEND_ALL; 174 break; 175 case 't': 176 globalSuspendPolicy = EventRequest.SUSPEND_EVENT_THREAD; 177 break; 178 case 'n': 179 globalSuspendPolicy = EventRequest.SUSPEND_NONE; 180 break; 181 default: 182 usage(); 183 } 184 String excString = args[3]; 185 if (excString.equals("null")) { 186 excString = null; 187 } 188 switch (args[0].toLowerCase().charAt(0)) { 189 case 'c': 190 goCaught(args[2], excString); 191 break; 192 case 'u': 193 goUncaught(args[2], excString); 194 break; 195 case 'n': 196 goNeither(args[2], excString); 197 break; 198 default: 199 usage(); 200 } 201 testName.append(args[0]); 202 testName.append(" "); 203 testName.append(args[1]); 204 testName.append(" "); 205 testName.append(args[2]); 206 } else { 207 usage(); 208 } 209 testName.append(")"); 210 211 summarize(testName.toString()); 212 } 213 214 static void summarize(String testName) throws Exception { 215 // final analyse 216 if (tooManySummary.length() > 0) { 217 System.out.println("\nSummary of tests with too many events:\n" + 218 tooManySummary.toString()); 219 } 220 if (notSentSummary.length() > 0) { 221 System.out.println("\nSummary of tests with expected events not sent:\n" + 222 notSentSummary.toString()); 223 } 224 if (unexpectedSummary.length() > 0) { 225 System.out.println("\nSummary of tests with events when none expected:\n" + 226 unexpectedSummary.toString()); 227 } 228 229 if (failureCount > 0) { 230 throw new Exception(testName + " FAILED " + 231 failureCount + " tests!"); 232 } else { 233 System.out.println("\n" + testName + " test PASSED"); 234 } 235 } 236 237 /** 238 * Target throws caught exception. 239 * Events if caught enabled. 240 */ 241 static void goCaught(String target, 242 String exceptionName) throws Exception { 243 goSuspendPolicy(target, true, exceptionName, 244 true, true); 245 goSuspendPolicy(target, true, exceptionName, 246 true, false); 247 goSuspendPolicy(target, false, exceptionName, 248 false, true); 249 goSuspendPolicy(target, false, exceptionName, 250 false, false); 251 } 252 253 /** 254 * Target throws uncaught exception. 255 * Events if uncaught enabled. 256 */ 257 static void goUncaught(String target, 258 String exceptionName) throws Exception { 259 goSuspendPolicy(target, true, exceptionName, 260 true, true); 261 goSuspendPolicy(target, true, exceptionName, 262 false, true); 263 goSuspendPolicy(target, false, exceptionName, 264 true, false); 265 goSuspendPolicy(target, false, exceptionName, 266 false, false); 267 } 268 269 /** 270 * Target doesn't throw named exception. No events. 271 */ 272 static void goNeither(String target, 273 String exceptionName) throws Exception { 274 goSuspendPolicy(target, false, exceptionName, 275 true, true); 276 goSuspendPolicy(target, false, exceptionName, 277 false, true); 278 goSuspendPolicy(target, false, exceptionName, 279 true, false); 280 goSuspendPolicy(target, false, exceptionName, 281 false, false); 282 } 283 284 /** 285 * Suspend policy should make no difference. 286 * Iterate over all of them. 287 */ 288 static void goSuspendPolicy(String target, 289 boolean expectedEvent, 290 String exceptionName, 291 boolean caught, boolean uncaught) throws Exception { 292 if (globalSuspendPolicy != -1) { 293 go(target, expectedEvent, exceptionName, 294 caught, uncaught, globalSuspendPolicy); 295 } else { 296 go(target, expectedEvent, exceptionName, 297 caught, uncaught, EventRequest.SUSPEND_ALL); 298 go(target, expectedEvent, exceptionName, 299 caught, uncaught, EventRequest.SUSPEND_EVENT_THREAD); 300 go(target, expectedEvent, exceptionName, 301 caught, uncaught, EventRequest.SUSPEND_NONE); 302 } 303 } 304 305 static void go(String target, 306 boolean expectedEvent, 307 String exceptionName, 308 boolean caught, boolean uncaught, 309 int suspendPolicy) throws Exception { 310 String description = target + " with " + 311 exceptionName + 312 "/caught=" + caught + 313 "/uncaught=" + uncaught + 314 " suspend="; 315 switch (suspendPolicy) { 316 case EventRequest.SUSPEND_ALL: 317 description += "All"; 318 break; 319 case EventRequest.SUSPEND_EVENT_THREAD: 320 description += "Thread"; 321 break; 322 case EventRequest.SUSPEND_NONE: 323 description += "None"; 324 break; 325 default: 326 throw new Exception("Test failure: bad suspend policy - " + 327 suspendPolicy); 328 } 329 description += "\n"; 330 331 System.out.print("\nTesting " + description); 332 333 ExceptionEvents aRun = new ExceptionEvents( 334 target, 335 exceptionName, caught, uncaught, 336 suspendPolicy); 337 aRun.startTests(); 338 aRun.analyse(expectedEvent, description); 339 } 340 341 void analyse(boolean expectedEvent, String description) { 342 if (expectedEvent) { 343 if (eventCount == 1) { 344 println("pass: got expected event"); 345 } else if (eventCount > 1) { 346 failure("FAILURE: expected only one event got: " + 347 eventCount); 348 tooManySummary.append(description); 349 ++failureCount; 350 } else { 351 failure("FAILURE: expected event not sent"); 352 notSentSummary.append(description); 353 ++failureCount; 354 } 355 } else { 356 if (eventCount > 0) { 357 failure("FAILURE: unexpected event sent"); 358 unexpectedSummary.append(description); 359 ++failureCount; 360 } else { 361 println("pass: as expected no event sent"); 362 } 363 } 364 } 365 366 367 /********** event handlers **********/ 368 369 public void exceptionThrown(ExceptionEvent event) { 370 if (event.request() == request) { 371 try { 372 System.out.print("ExceptionEvent: "); 373 System.out.print("" + event.exception().referenceType().name()); 374 Location loc = event.location(); 375 System.out.print(" @ " + loc.method().name()); 376 System.out.print(":" + loc.lineNumber()); 377 } catch (VMDisconnectedException exc) { 378 System.out.print("Oops - " + exc.toString()); 379 } 380 System.out.println(); 381 eventCount++; 382 } else { 383 System.out.print("alien exception: "); 384 try { 385 println(event.toString()); 386 } catch (VMDisconnectedException exc) { 387 println("Oops - " + exc.toString()); 388 } 389 } 390 } 391 392 /** 393 * Turn off default Exception Handling 394 */ 395 protected void createDefaultExceptionRequest() { 396 } 397 398 /********** test core **********/ 399 400 protected void runTests() throws Exception { 401 /* 402 * Get to the top of main() 403 */ 404 startToMain(target); 405 406 ReferenceType exceptionClass; 407 408 if (exceptionName == null) { 409 exceptionClass = null; 410 } else { 411 exceptionClass = findReferenceType(exceptionName); 412 if (exceptionName == null) { 413 throw new Exception("test failure - cannot find: " + 414 exceptionName); 415 } 416 } 417 418 request = eventRequestManager().createExceptionRequest(exceptionClass, 419 caught, uncaught); 420 request.addClassExclusionFilter("java.*"); 421 request.addClassExclusionFilter("javax.*"); 422 request.addClassExclusionFilter("sun.*"); 423 request.addClassExclusionFilter("com.sun.*"); 424 request.addClassExclusionFilter("com.oracle.*"); 425 request.addClassExclusionFilter("oracle.*"); 426 request.addClassExclusionFilter("jdk.internal.*"); 427 request.setSuspendPolicy(suspendPolicy); 428 request.enable(); 429 430 listenUntilVMDisconnect(); 431 } 432 }