RetentionAnnoCombo.java revision 2933:49d207bf704d
1/* 2 * Copyright (c) 2012, 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 8002157 27 * @author sogoel 28 * @summary Combo test for all possible combinations for Retention Values 29 * @modules jdk.compiler 30 * @build Helper 31 * @compile RetentionAnnoCombo.java 32 * @run main RetentionAnnoCombo 33 */ 34 35import java.util.HashMap; 36import java.util.Map; 37 38import javax.tools.DiagnosticCollector; 39import javax.tools.JavaFileObject; 40import javax.tools.Diagnostic; 41 42/* 43 * Generate all combinations for the use of @Retention on base anno or container 44 * anno or both. The test passes if valid test src compile as expected and 45 * and invalid test src fail as expected. 46 * Repeating annotations used only on class for these generated test src. 47 */ 48 49public class RetentionAnnoCombo extends Helper { 50 static int errors = 0; 51 static boolean exitMode = false; 52 static { 53 String exitOnFail = System.getenv("EXIT_ON_FAIL"); 54 if (exitOnFail == null || exitOnFail == "" ) { 55 exitMode = false; 56 } 57 else { 58 if (exitOnFail.equalsIgnoreCase("YES") || 59 exitOnFail.equalsIgnoreCase("Y") || 60 exitOnFail.equalsIgnoreCase("TRUE") || 61 exitOnFail.equalsIgnoreCase("T")) { 62 exitMode = true; 63 } 64 } 65 } 66 67 public static void main(String args[]) throws Exception { 68 new RetentionAnnoCombo().runTest(); 69 } 70 71 public void runTest() throws Exception { 72 73 /* 4x4 matrix for Retention values SOURCE, DEFAULT, CLASS, RUNTIME 74 * i -> Retention value on ContainerAnno 75 * j -> Retention value on BaseAnno 76 * 1 -> retention value combo should compile 77 */ 78 int[][] retention = { {1, 0, 0, 0}, 79 {1, 1, 1, 0}, 80 {1, 1, 1, 0}, 81 {1, 1, 1, 1} }; 82 83 Map<Integer, String> retMap = setRetentionValMatrix(); 84 String contents = ""; 85 boolean result = false; 86 int testCtr = 0; 87 for (int i = 0; i < 4 ; i ++) { 88 for (int j = 0; j < 4; j++ ) { 89 testCtr++; 90 String className = "RetentionTest_"+i+"_"+j; 91 contents = getContent(className, retMap, i, j); 92 if (retention[i][j] == 1) { 93 // Code generated should compile 94 result = getCompileResult(contents,className, true); 95 if (!result) { 96 error("FAIL: " + className + " did not compile as expected!", contents); 97 } 98 } else { 99 result = getCompileResult(contents,className, false); 100 if (!result) { 101 error("FAIL: " + className + " compiled unexpectedly!", contents); 102 } 103 } 104 if (result) { 105 System.out.println("Test passed for className = " + className); 106 } 107 } 108 } 109 110 System.out.println("Total number of tests run: " + testCtr); 111 System.out.println("Total number of errors: " + errors); 112 113 if (errors > 0) 114 throw new Exception(errors + " errors found"); 115 } 116 117 private boolean getCompileResult(String contents, String className, 118 boolean shouldCompile) throws Exception{ 119 120 DiagnosticCollector<JavaFileObject> diagnostics = 121 new DiagnosticCollector<JavaFileObject>(); 122 boolean ok = compileCode(className, contents, diagnostics); 123 124 String expectedErrKey = "compiler.err.invalid.repeatable" + 125 ".annotation.retention"; 126 if (!shouldCompile && !ok) { 127 for (Diagnostic<?> d : diagnostics.getDiagnostics()) { 128 if (!((d.getKind() == Diagnostic.Kind.ERROR) && 129 d.getCode().contains(expectedErrKey))) { 130 error("FAIL: Incorrect error given, expected = " 131 + expectedErrKey + ", Actual = " + d.getCode() 132 + " for className = " + className, contents); 133 } 134 } 135 } 136 137 return (shouldCompile == ok); 138 } 139 140 private Map<Integer,String> setRetentionValMatrix() { 141 HashMap<Integer,String> hm = new HashMap<>(); 142 hm.put(0,"SOURCE"); 143 hm.put(1,"DEFAULT"); 144 hm.put(2,"CLASS"); 145 hm.put(3,"RUNTIME"); 146 return hm; 147 } 148 149 private String getContent(String className, Map<Integer, String> retMap, 150 int i, int j) { 151 152 String retContainerVal = retMap.get(i).toString(); 153 String retBaseVal = retMap.get(j).toString(); 154 String replacedRetBaseVal = "", replacedRetCAVal = ""; 155 String retention = Helper.ContentVars.RETENTION.getVal(); 156 157 // @Retention is available as default for both base and container anno 158 if (retContainerVal.equalsIgnoreCase("DEFAULT") 159 && retBaseVal.equalsIgnoreCase("DEFAULT")) { 160 replacedRetBaseVal = ""; 161 replacedRetCAVal = ""; 162 // @Retention is available as default for container anno 163 } else if (retContainerVal.equalsIgnoreCase("DEFAULT")) { 164 replacedRetBaseVal = retention.replace("#VAL", retBaseVal); 165 replacedRetCAVal = ""; 166 // @Retention is available as default for base anno 167 } else if (retBaseVal.equalsIgnoreCase("DEFAULT")) { 168 replacedRetBaseVal = ""; 169 replacedRetCAVal = retention.replace("#VAL", retContainerVal); 170 // @Retention is not available as default for both base and container anno 171 } else { 172 replacedRetBaseVal = retention.replace("#VAL", retBaseVal); 173 replacedRetCAVal = retention.replace("#VAL", retContainerVal); 174 } 175 176 StringBuilder annoData = new StringBuilder(); 177 annoData.append(Helper.ContentVars.IMPORTCONTAINERSTMTS.getVal()) 178 .append(Helper.ContentVars.IMPORTRETENTION.getVal()) 179 .append(replacedRetCAVal) 180 .append(Helper.ContentVars.CONTAINER.getVal()) 181 .append(Helper.ContentVars.REPEATABLE.getVal()) 182 .append(replacedRetBaseVal) 183 .append(Helper.ContentVars.BASE.getVal()); 184 185 String contents = annoData 186 + Helper.ContentVars.REPEATABLEANNO.getVal() 187 + "\nclass "+ className + "{}"; 188 return contents; 189 } 190 191 private void error(String msg,String... contents) throws Exception { 192 System.out.println("error: " + msg); 193 errors++; 194 if (contents.length == 1) { 195 System.out.println("Contents = " + contents[0]); 196 } 197 // Test exits as soon as it gets a failure 198 if (exitMode) throw new Exception(); 199 } 200} 201 202