1 /* 2 * @test /nodynamiccopyright/ 3 * @bug 6827009 8078561 4 * @summary Positive tests for strings in switch with few alternatives. 5 * @compile/fail/ref=OneCaseSwitches.out -XDrawDiagnostics -source 6 OneCaseSwitches.java 6 * @compile OneCaseSwitches.java 7 * @run main OneCaseSwitches 8 * @author Joseph D. Darcy 9 */ 10 11 import java.lang.reflect.*; 12 import java.lang.annotation.*; 13 import java.util.*; 14 import static java.lang.annotation.RetentionPolicy.*; 15 16 public class OneCaseSwitches { 17 @Retention(RUNTIME) 18 @interface TestMeForNull {} 19 20 @TestMeForNull 21 public static int zeroCasesNoDefault(String s, Set<String> stringSet, boolean expected) { 22 int failures = 0; 23 switch(s) { 24 } 25 return failures; 26 } 27 28 @TestMeForNull 29 public static int zeroCasesWithDefault(String s, Set<String> stringSet, boolean expected) { 30 int failures = 2; 31 boolean addResult; 32 33 switch(s) { 34 default: 35 failures = 0; 36 addResult = stringSet.add(s); 37 if (addResult != expected) { 38 failures++; 39 System.err.println("zeroCaseWithDefault: Expectedly got add result of " + addResult + 40 " on string " + s); 41 } 42 } 43 44 return failures; 45 } 46 47 @TestMeForNull 48 public static int zeroCasesWithDefaultBreak(String s, Set<String> stringSet, boolean expected) { 49 int failures = 2; 50 boolean addResult; 51 52 switch(s) { 53 default: 54 failures = zeroCasesWithDefault(s, stringSet, expected); 55 break; 56 } 57 58 return failures; 59 } 60 61 @TestMeForNull 62 public static int oneCaseNoDefault(String s, Set<String> stringSet, boolean expected) { 63 int failures = 2; 64 boolean addResult; 65 66 switch(s) { 67 case "foo": 68 failures = 0; 69 addResult = stringSet.add(s); 70 if (addResult != expected) { 71 failures++; 72 System.err.println("oneCaseNoDefault: Unexpectedly got add result of " + addResult + 73 " on string " + s); 74 } 75 } 76 77 return failures; 78 } 79 80 @TestMeForNull 81 public static int oneCaseNoDefaultBreak(String s, Set<String> stringSet, boolean expected) { 82 int failures = 2; 83 boolean addResult; 84 85 switch(s) { 86 case "foo": 87 failures = oneCaseNoDefaultBreak(s, stringSet, expected); 88 break; 89 } 90 91 return failures; 92 } 93 94 @TestMeForNull 95 public static int oneCaseWithDefault(String s, Set<String> stringSet, boolean expected) { 96 int failures = 2; 97 boolean addResult;; 98 99 switch(s) { 100 case "foo": 101 failures = 0; 102 addResult = stringSet.add(s); 103 if (addResult != expected) { 104 failures++; 105 System.err.println("oneCaseNoDefault: Expectedly got add result of " + addResult + 106 " on string " + s); 107 } 108 break; 109 default: 110 break; 111 } 112 113 return failures; 114 } 115 116 @TestMeForNull 117 public static int oneCaseBreakOnly(String s, Set<String> stringSet, boolean expected) { 118 int failures = 1; 119 switch(s) { 120 case "foo": 121 break; 122 } 123 failures = 0; 124 return failures; 125 } 126 127 @TestMeForNull 128 public static int oneCaseDefaultBreakOnly(String s, Set<String> stringSet, boolean expected) { 129 int failures = 1; 130 switch(s) { 131 default: 132 break; 133 } 134 failures = 0; 135 return failures; 136 } 137 138 139 static int testNullBehavior() { 140 int failures = 0; 141 int count = 0; 142 143 Method[] methods = OneCaseSwitches.class.getDeclaredMethods(); 144 145 try { 146 for(Method method : methods) { 147 count++; 148 try { 149 if (method.isAnnotationPresent(TestMeForNull.class)) { 150 System.out.println("Testing method " + method); 151 method.invoke(null, (String)null, emptyStringSet, false); 152 failures++; 153 System.err.println("Didn't get NPE as expected from " + method); 154 } 155 } catch (InvocationTargetException ite) { // Expected 156 Throwable targetException = ite.getTargetException(); 157 if (! (targetException instanceof NullPointerException)) { 158 failures++; // Wrong exception thrown 159 System.err.println("Didn't get expected target exception NPE, got " + 160 ite.getClass().getName()); 161 } 162 } 163 } 164 } catch (Exception e) { 165 throw new RuntimeException(e); 166 } 167 168 if (count == 0) { 169 failures++; 170 System.err.println("Did not find any annotated methods."); 171 } 172 return failures; 173 } 174 175 static int testZeroCases() { 176 int failures = 0; 177 Set<String> noDefaultSet = new HashSet<String>(); 178 Set<String> defaultSet = new HashSet<String>(); 179 180 zeroCasesNoDefault(FOO, noDefaultSet, false); 181 for(String word : words) { 182 zeroCasesNoDefault(word, noDefaultSet, false); 183 } 184 185 if (!noDefaultSet.isEmpty()) { 186 failures++; 187 System.err.println("Non-empty set after zeroCasesNoDefault"); 188 } 189 190 for(String word : words) { 191 zeroCasesWithDefault(word, defaultSet, true); 192 } 193 if (defaultSet.size() != words.length) { 194 failures++; 195 System.err.println("Missing strings after zeroCasesWithDefault"); 196 } 197 198 return failures; 199 } 200 201 static int testOneCaseNoDefault() { 202 int failures = 0; 203 Set<String> s = new HashSet<String>(); 204 s.add("foo"); 205 Set<String> fooSet = Collections.unmodifiableSet(s); 206 Set<String> testSet = new HashSet<String>(); 207 208 oneCaseNoDefault(FOO, testSet, true); 209 if (!testSet.equals(fooSet)) { 210 failures++; 211 System.err.println("Unexpected result from oneCaseNoDefault: didn't get {\"Foo\"}"); 212 } 213 214 for(String word : words) { 215 oneCaseNoDefault(word, testSet, false); 216 } 217 if (!testSet.equals(fooSet)) { 218 failures++; 219 System.err.println("Unexpected result from oneCaseNoDefault: didn't get {\"Foo\"}"); 220 } 221 222 return failures; 223 } 224 225 static int testBreakOnly() { 226 int failures = 0; 227 228 for(String word : words) { 229 failures += oneCaseBreakOnly(word, emptyStringSet, true); 230 failures += oneCaseDefaultBreakOnly(word, emptyStringSet, true); 231 } 232 233 return failures; 234 } 235 236 static int testExpressionEval() { 237 String s = "a"; 238 int errors = 2; 239 240 System.out.println("Testing expression evaluation."); 241 242 switch (s + s) { 243 case "aa": 244 errors = 0; 245 break; 246 247 case "aaaa": 248 errors = 1; 249 System.err.println("Suspected bad expression evaluation."); 250 break; 251 252 default: 253 throw new RuntimeException("Should not reach here."); 254 } 255 return errors; 256 } 257 258 static final String FOO = "foo"; 259 260 static final String[] words = {"baz", 261 "quux", 262 "wombat", 263 "\u0ccc\u0012"}; // hash collision with "foo" 264 265 final static Set<String> emptyStringSet = Collections.emptySet(); 266 267 public static void main(String... args) { 268 int failures = 0; 269 270 failures += testNullBehavior(); 271 failures += testZeroCases(); 272 failures += testOneCaseNoDefault(); 273 failures += testBreakOnly(); 274 failures += testExpressionEval(); 275 276 if (failures > 0) { 277 throw new RuntimeException(); 278 } 279 } 280 }