1#!/bin/sh 2 3# 4# Copyright (c) 2004, Oracle and/or its affiliates. All rights reserved. 5# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 6# 7# This code is free software; you can redistribute it and/or modify it 8# under the terms of the GNU General Public License version 2 only, as 9# published by the Free Software Foundation. 10# 11# This code is distributed in the hope that it will be useful, but WITHOUT 12# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14# version 2 for more details (a copy is included in the LICENSE file that 15# accompanied this code). 16# 17# You should have received a copy of the GNU General Public License version 18# 2 along with this work; if not, write to the Free Software Foundation, 19# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20# 21# Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22# or visit www.oracle.com if you need additional information or have any 23# questions. 24# 25 26# 27# @test 28# @bug 4833089 4992454 29# @summary Check for proper handling of uncaught exceptions 30# @author Martin Buchholz 31# 32# @run shell UncaughtExceptions.sh 33 34# To run this test manually, simply do ./UncaughtExceptions.sh 35 36 java="${TESTJAVA+${TESTJAVA}/bin/}java" 37javac="${COMPILEJAVA+${COMPILEJAVA}/bin/}javac" 38 39failed="" 40Fail() { echo "FAIL: $1"; failed="${failed}."; } 41 42Die() { printf "%s\n" "$*"; exit 1; } 43 44Sys() { 45 "$@"; rc="$?"; 46 test "$rc" -eq 0 || Die "Command \"$*\" failed with exitValue $rc"; 47} 48 49HorizontalRule() { 50 echo "-----------------------------------------------------------------" 51} 52 53Bottom() { 54 test "$#" = 1 -a "$1" = "Line" || Die "Usage: Bottom Line" 55 56 HorizontalRule 57 if test -n "$failed"; then 58 count=`printf "%s" "$failed" | wc -c | tr -d ' '` 59 echo "FAIL: $count tests failed" 60 exit 1 61 else 62 echo "PASS: all tests gave expected results" 63 exit 0 64 fi 65} 66 67Cleanup() { Sys rm -f Seppuku* OK.class; } 68 69set -u 70 71checkOutput() { 72 name="$1" expected="$2" got="$3" 73 printf "$name:\n"; cat "$got" 74 if test -z "$expected"; then 75 test "`cat $got`" != "" && \ 76 Fail "Unexpected $name: `cat $got`" 77 else 78 grep "$expected" "$got" >/dev/null || \ 79 Fail "Expected \"$expected\", got `cat $got`" 80 fi 81} 82 83CheckCommandResults() { 84 expectedRC="$1" expectedOut="$2" expectedErr="$3"; shift 3 85 saveFailed="${failed}" 86 "$@" >TmpTest.Out 2>TmpTest.Err; rc="$?"; 87 printf "==> %s (rc=%d)\n" "$*" "$rc" 88 checkOutput "stdout" "$expectedOut" "TmpTest.Out" 89 checkOutput "stderr" "$expectedErr" "TmpTest.Err" 90 test "${saveFailed}" = "${failed}" && \ 91 echo "PASS: command completed as expected" 92 Sys rm -f TmpTest.Out TmpTest.Err 93} 94 95Run() { 96 expectedRC="$1" expectedOut="$2" expectedErr="$3" mainBody="$4" 97 cat > Seppuku.java <<EOJAVA 98import static java.lang.Thread.*; 99import static java.lang.System.*; 100 101class OK implements UncaughtExceptionHandler { 102 public void uncaughtException(Thread t, Throwable e) { 103 out.println("OK"); 104 } 105} 106 107class NeverInvoked implements UncaughtExceptionHandler { 108 public void uncaughtException(Thread t, Throwable e) { 109 err.println("Test failure: This handler should never be invoked!"); 110 } 111} 112 113public class Seppuku extends Thread implements Runnable { 114 public static void seppuku() { throw new RuntimeException("Seppuku!"); } 115 116 public void run() { seppuku(); } 117 118 public static void main(String[] args) throws Exception { 119 $mainBody 120 } 121} 122EOJAVA 123 124 Sys "$javac" ${TESTJAVACOPTS} ${TESTTOOLVMOPTS} "Seppuku.java" 125 CheckCommandResults "$expectedRC" "$expectedOut" "$expectedErr" \ 126 "$java" "Seppuku" 127 Cleanup 128} 129 130#---------------------------------------------------------------- 131# A thread is never alive after you've join()ed it. 132#---------------------------------------------------------------- 133Run 0 "OK" "Exception in thread \"Thread-0\".*Seppuku" " 134 Thread t = new Seppuku(); 135 t.start(); t.join(); 136 if (! t.isAlive()) 137 out.println(\"OK\");" 138 139#---------------------------------------------------------------- 140# Even the main thread is mortal - here it terminates "abruptly" 141#---------------------------------------------------------------- 142Run 1 "OK" "Exception in thread \"main\".*Seppuku" " 143 final Thread mainThread = currentThread(); 144 new Thread() { public void run() { 145 try { mainThread.join(); } 146 catch (InterruptedException e) {} 147 if (! mainThread.isAlive()) 148 out.println(\"OK\"); 149 }}.start(); 150 seppuku();" 151 152#---------------------------------------------------------------- 153# Even the main thread is mortal - here it terminates normally. 154#---------------------------------------------------------------- 155Run 0 "OK" "" " 156 final Thread mainThread = currentThread(); 157 new Thread() { public void run() { 158 try { mainThread.join(); } 159 catch (InterruptedException e) {} 160 if (! mainThread.isAlive()) 161 out.println(\"OK\"); 162 }}.start();" 163 164#---------------------------------------------------------------- 165# Check uncaught exception handler mechanism on the main thread. 166# Check that thread-level handler overrides global default handler. 167#---------------------------------------------------------------- 168Run 1 "OK" "" " 169 currentThread().setUncaughtExceptionHandler(new OK()); 170 setDefaultUncaughtExceptionHandler(new NeverInvoked()); 171 seppuku();" 172 173Run 1 "OK" "" " 174 setDefaultUncaughtExceptionHandler(new OK()); 175 seppuku();" 176 177#---------------------------------------------------------------- 178# Check uncaught exception handler mechanism on non-main threads. 179#---------------------------------------------------------------- 180Run 0 "OK" "" " 181 Thread t = new Seppuku(); 182 t.setUncaughtExceptionHandler(new OK()); 183 t.start();" 184 185Run 0 "OK" "" " 186 setDefaultUncaughtExceptionHandler(new OK()); 187 new Seppuku().start();" 188 189#---------------------------------------------------------------- 190# Test ThreadGroup based uncaught exception handler mechanism. 191# Since the handler for the main thread group cannot be changed, 192# there are no tests for the main thread here. 193#---------------------------------------------------------------- 194Run 0 "OK" "" " 195 setDefaultUncaughtExceptionHandler(new NeverInvoked()); 196 new Thread( 197 new ThreadGroup(\"OK\") { 198 public void uncaughtException(Thread t, Throwable e) { 199 out.println(\"OK\");}}, 200 new Seppuku() 201 ).start();" 202 203Cleanup 204 205Bottom Line 206