changeset 1104:b5f788c594fe

7901279: jmh-core-ct compilation tests should also do annprocess-backed tests
author shade
date Wed, 28 Jan 2015 16:04:02 +0300
parents 0f207fdbf463
children a355260808dc
files jmh-core-ct/pom.xml jmh-core-ct/src/test/java/org/openjdk/jmh/ct/CompileTest.java jmh-generator-annprocess/src/main/java/org/openjdk/jmh/generators/annotations/APClassInfo.java
diffstat 3 files changed, 138 insertions(+), 69 deletions(-) [+]
line wrap: on
line diff
--- a/jmh-core-ct/pom.xml	Thu Jan 22 19:04:23 2015 +0300
+++ b/jmh-core-ct/pom.xml	Wed Jan 28 16:04:02 2015 +0300
@@ -51,6 +51,11 @@
         </dependency>
         <dependency>
             <groupId>org.openjdk.jmh</groupId>
+            <artifactId>jmh-generator-annprocess</artifactId>
+            <version>${project.version}</version>
+        </dependency>
+        <dependency>
+            <groupId>org.openjdk.jmh</groupId>
             <artifactId>jmh-generator-reflection</artifactId>
             <version>${project.version}</version>
         </dependency>
@@ -111,6 +116,12 @@
                 </configuration>
             </plugin>
         </plugins>
+
+        <resources>
+            <resource>
+                <directory>${project.build.testSourceDirectory}</directory>
+            </resource>
+        </resources>
     </build>
 
     <profiles>
@@ -127,7 +138,7 @@
                         <version>2.14.1</version>
                         <configuration>
                             <redirectTestOutputToFile>true</redirectTestOutputToFile>
-                            <argLine>-Djmh.ct.generator=reflection</argLine>
+                            <argLine>-Djmh.ct.generator=annprocess</argLine>
                         </configuration>
                     </plugin>
                 </plugins>
@@ -150,6 +161,23 @@
                 </plugins>
             </build>
         </profile>
+
+        <profile>
+            <id>reflection</id>
+            <build>
+                <plugins>
+                    <plugin>
+                        <groupId>org.apache.maven.plugins</groupId>
+                        <artifactId>maven-surefire-plugin</artifactId>
+                        <version>2.14.1</version>
+                        <configuration>
+                            <redirectTestOutputToFile>true</redirectTestOutputToFile>
+                            <argLine>-Djmh.ct.generator=reflection</argLine>
+                        </configuration>
+                    </plugin>
+                </plugins>
+            </build>
+        </profile>
     </profiles>
 
 </project>
--- a/jmh-core-ct/src/test/java/org/openjdk/jmh/ct/CompileTest.java	Thu Jan 22 19:04:23 2015 +0300
+++ b/jmh-core-ct/src/test/java/org/openjdk/jmh/ct/CompileTest.java	Wed Jan 28 16:04:02 2015 +0300
@@ -27,7 +27,10 @@
 import junit.framework.Assert;
 import org.openjdk.jmh.generators.asm.ASMGeneratorSource;
 import org.openjdk.jmh.generators.core.BenchmarkGenerator;
+import org.openjdk.jmh.generators.core.GeneratorSource;
 import org.openjdk.jmh.generators.reflection.RFGeneratorSource;
+import org.openjdk.jmh.util.FileUtils;
+import org.openjdk.jmh.util.Utils;
 
 import javax.tools.Diagnostic;
 import javax.tools.DiagnosticCollector;
@@ -39,6 +42,8 @@
 import javax.tools.ToolProvider;
 import java.io.File;
 import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
 import java.net.URI;
 import java.util.ArrayList;
 import java.util.Collection;
@@ -50,15 +55,17 @@
     private static final String GENERATOR_TYPE = System.getProperty("jmh.ct.generator", "notset");
 
     public static void assertFail(Class<?> klass) {
-        InMemoryGeneratorDestination destination = doTest(klass);
-        if (!destination.hasErrors()) {
+        InMemoryGeneratorDestination destination = new InMemoryGeneratorDestination();
+        boolean success = doTest(klass, destination);
+        if (success) {
             Assert.fail("Should have failed.");
         }
     }
 
     public static void assertFail(Class<?> klass, String error) {
-        InMemoryGeneratorDestination destination = doTest(klass);
-        if (!destination.hasErrors()) {
+        InMemoryGeneratorDestination destination = new InMemoryGeneratorDestination();
+        boolean success = doTest(klass, destination);
+        if (success) {
             Assert.fail("Should have failed.");
         }
 
@@ -71,7 +78,38 @@
     }
 
     public static void assertOK(Class<?> klass) {
-        InMemoryGeneratorDestination destination = doTest(klass);
+        InMemoryGeneratorDestination destination = new InMemoryGeneratorDestination();
+        boolean success = doTest(klass, destination);
+        if (!success) {
+            Assert.fail("Should have passed.");
+        }
+    }
+
+    private static boolean doTest(Class<?> klass, InMemoryGeneratorDestination destination) {
+        if (GENERATOR_TYPE.equalsIgnoreCase("reflection")) {
+            RFGeneratorSource source = new RFGeneratorSource();
+            source.processClasses(klass);
+            return doTestOther(source, destination);
+        } else if (GENERATOR_TYPE.equalsIgnoreCase("asm")) {
+            ASMGeneratorSource source = new ASMGeneratorSource();
+            String name = "/" + klass.getCanonicalName().replaceAll("\\.", "/") + ".class";
+            try {
+                source.processClass(klass.getResourceAsStream(name));
+            } catch (IOException e) {
+                throw new IllegalStateException(name, e);
+            }
+            return doTestOther(source, destination);
+        } else if (GENERATOR_TYPE.equalsIgnoreCase("annprocess")) {
+            return doTestAnnprocess(klass, destination);
+        } else
+            throw new IllegalStateException("Unhandled compile test generator: " + GENERATOR_TYPE);
+    }
+
+
+    public static boolean doTestOther(GeneratorSource source, InMemoryGeneratorDestination destination) {
+        BenchmarkGenerator gen = new BenchmarkGenerator();
+        gen.generate(source, destination);
+        gen.complete(source, destination);
 
         if (destination.hasErrors()) {
             StringBuilder sb = new StringBuilder();
@@ -79,7 +117,7 @@
             for (String e : destination.getErrors()) {
                 sb.append(e).append("\n");
             }
-            Assert.fail(sb.toString());
+            return false;
         }
 
         DiagnosticCollector<JavaFileObject> diagnostics = new DiagnosticCollector<JavaFileObject>();
@@ -98,7 +136,7 @@
             sources.add(new JavaSourceFromString(e.getKey(), e.getValue()));
         }
 
-        JavaCompiler.CompilationTask task = javac.getTask(null, fm, diagnostics, null, null, sources);
+        JavaCompiler.CompilationTask task = javac.getTask(null, fm, diagnostics, Collections.singleton("-proc:none"), null, sources);
         boolean success = task.call();
 
         if (!success) {
@@ -108,7 +146,49 @@
             for (Diagnostic diagnostic : diagnostics.getDiagnostics()) {
                 System.out.println(diagnostic.getKind() + " at line " + diagnostic.getLineNumber() + ": " + diagnostic.getMessage(null));
             }
-            Assert.fail("Unable to compile the generated code");
+        }
+
+        return success;
+    }
+
+    private static boolean doTestAnnprocess(Class<?> klass, InMemoryGeneratorDestination destination) {
+        DiagnosticCollector<JavaFileObject> diagnostics = new DiagnosticCollector<JavaFileObject>();
+
+        JavaCompiler javac = ToolProvider.getSystemJavaCompiler();
+        StandardJavaFileManager fm = javac.getStandardFileManager(null, null, null);
+
+        try {
+            fm.setLocation(StandardLocation.CLASS_OUTPUT, Collections.singleton(new File(System.getProperty("java.io.tmpdir"))));
+        } catch (IOException e) {
+            Assert.fail(e.getMessage());
+        }
+
+        String name = "/" + klass.getCanonicalName().replaceAll("\\.", "/") + ".java";
+        String shortName = klass.getName();
+
+        InputStream stream = klass.getResourceAsStream(name);
+        Assert.assertNotNull(name + " is not found", stream);
+
+        try {
+            Collection<String> lines = FileUtils.readAllLines(new InputStreamReader(stream));
+            String file = Utils.join(lines, "\n");
+
+            Collection<JavaSourceFromString> sources = Collections.singleton(new JavaSourceFromString(shortName, file));
+            JavaCompiler.CompilationTask task = javac.getTask(null, fm, diagnostics, null, null, sources);
+
+            boolean success = task.call();
+
+            if (!success) {
+                for (JavaSourceFromString src : sources) {
+                    System.out.println(src.getCharContent(false));
+                }
+                for (Diagnostic diagnostic : diagnostics.getDiagnostics()) {
+                    destination.printError(diagnostic.getKind() + " at line " + diagnostic.getLineNumber() + ": " + diagnostic.getMessage(null));
+                }
+            }
+            return success;
+        } catch (IOException e) {
+            return false;
         }
     }
 
@@ -126,43 +206,4 @@
         }
     }
 
-    private static InMemoryGeneratorDestination doTest(Class<?> klass) {
-        if (GENERATOR_TYPE.equalsIgnoreCase("reflection")) {
-            return doTestReflection(klass);
-        }
-        if (GENERATOR_TYPE.equalsIgnoreCase("asm")) {
-            return doTestAsm(klass);
-        }
-        throw new IllegalStateException("Unhandled compile test generator: " + GENERATOR_TYPE);
-    }
-
-    private static InMemoryGeneratorDestination doTestReflection(Class<?> klass) {
-        RFGeneratorSource source = new RFGeneratorSource();
-        InMemoryGeneratorDestination destination = new InMemoryGeneratorDestination();
-        source.processClasses(klass);
-
-        BenchmarkGenerator gen = new BenchmarkGenerator();
-        gen.generate(source, destination);
-        gen.complete(source, destination);
-        return destination;
-    }
-
-    private static InMemoryGeneratorDestination doTestAsm(Class<?> klass) {
-        ASMGeneratorSource source = new ASMGeneratorSource();
-        InMemoryGeneratorDestination destination = new InMemoryGeneratorDestination();
-
-        String name = "/" + klass.getCanonicalName().replaceAll("\\.", "/") + ".class";
-        try {
-            source.processClass(klass.getResourceAsStream(name));
-        } catch (IOException e) {
-            throw new IllegalStateException(name, e);
-        }
-
-        BenchmarkGenerator gen = new BenchmarkGenerator();
-        gen.generate(source, destination);
-        gen.complete(source, destination);
-        return destination;
-    }
-
-
 }
--- a/jmh-generator-annprocess/src/main/java/org/openjdk/jmh/generators/annotations/APClassInfo.java	Thu Jan 22 19:04:23 2015 +0300
+++ b/jmh-generator-annprocess/src/main/java/org/openjdk/jmh/generators/annotations/APClassInfo.java	Wed Jan 28 16:04:02 2015 +0300
@@ -48,7 +48,7 @@
 class APClassInfo extends APMetadataInfo implements ClassInfo {
 
     private final TypeElement el;
-    private final boolean isPrimitive;
+    private final boolean isSpecial;
     private final TypeMirror mirror;
 
     public APClassInfo(ProcessingEnvironment processEnv, TypeElement element) {
@@ -57,30 +57,30 @@
             throw new IllegalArgumentException("element is null");
         }
         this.el = element;
-        this.isPrimitive = false;
+        this.isSpecial = false;
         this.mirror = null;
     }
 
     public APClassInfo(ProcessingEnvironment processEnv, TypeMirror mirror) {
         super(processEnv, null);
         this.mirror = mirror;
-        this.isPrimitive = mirror.getKind().isPrimitive();
-        if (!isPrimitive) {
+        this.isSpecial = mirror.getKind().isPrimitive() || (mirror.getKind() == TypeKind.ARRAY);
+        if (isSpecial) {
+            this.el = null;
+        } else {
             this.el = (TypeElement) processEnv.getTypeUtils().asElement(mirror);
-        } else {
-            this.el = null;
         }
     }
 
     @Override
     public <T extends Annotation> T getAnnotation(Class<T> annClass) {
-        if (isPrimitive) return null;
+        if (isSpecial) return null;
         return el.getAnnotation(annClass);
     }
 
     @Override
     public Collection<MethodInfo> getConstructors() {
-        if (isPrimitive) return Collections.emptyList();
+        if (isSpecial) return Collections.emptyList();
         Collection<MethodInfo> mis = new ArrayList<MethodInfo>();
         for (ExecutableElement e : ElementFilter.constructorsIn(el.getEnclosedElements())) {
             mis.add(new APMethodInfo(processEnv, this, e));
@@ -90,19 +90,19 @@
 
     @Override
     public String getName() {
-        if (isPrimitive) return mirror.toString();
+        if (isSpecial) return mirror.toString();
         return el.getSimpleName().toString();
     }
 
     @Override
     public String getQualifiedName() {
-        if (isPrimitive) return mirror.toString();
+        if (isSpecial) return mirror.toString();
         return el.getQualifiedName().toString();
     }
 
     @Override
     public Collection<FieldInfo> getFields() {
-        if (isPrimitive) return Collections.emptyList();
+        if (isSpecial) return Collections.emptyList();
         List<FieldInfo> ls = new ArrayList<FieldInfo>();
         for (VariableElement e : ElementFilter.fieldsIn(el.getEnclosedElements())) {
             ls.add(new APFieldInfo(processEnv, e));
@@ -112,7 +112,7 @@
 
     @Override
     public Collection<MethodInfo> getMethods() {
-        if (isPrimitive) return Collections.emptyList();
+        if (isSpecial) return Collections.emptyList();
         Collection<MethodInfo> mis = new ArrayList<MethodInfo>();
         for (ExecutableElement e : ElementFilter.methodsIn(el.getEnclosedElements())) {
             mis.add(new APMethodInfo(processEnv, this, e));
@@ -122,7 +122,7 @@
 
     @Override
     public String getPackageName() {
-        if (isPrimitive) return "";
+        if (isSpecial) return "";
         Element walk = el;
         while (walk.getKind() != ElementKind.PACKAGE) {
             walk = walk.getEnclosingElement();
@@ -132,7 +132,7 @@
 
     @Override
     public ClassInfo getSuperClass() {
-        if (isPrimitive) return null;
+        if (isSpecial) return null;
         TypeMirror superclass = el.getSuperclass();
         if (superclass.getKind() == TypeKind.NONE) {
             return null;
@@ -144,7 +144,7 @@
 
     @Override
     public ClassInfo getDeclaringClass() {
-        if (isPrimitive) return null;
+        if (isSpecial) return null;
         Element enclosingElement = el.getEnclosingElement();
         if (enclosingElement.getKind() == ElementKind.CLASS) {
             return new APClassInfo(processEnv, (TypeElement) enclosingElement);
@@ -155,37 +155,37 @@
 
     @Override
     public boolean isAbstract() {
-        if (isPrimitive) return false;
+        if (isSpecial) return false;
         return el.getModifiers().contains(Modifier.ABSTRACT);
     }
 
     @Override
     public boolean isPublic() {
-        if (isPrimitive) return true;
+        if (isSpecial) return true;
         return el.getModifiers().contains(Modifier.PUBLIC);
     }
 
     @Override
     public boolean isStrictFP() {
-        if (isPrimitive) return false;
+        if (isSpecial) return false;
         return el.getModifiers().contains(Modifier.STRICTFP);
     }
 
     @Override
     public boolean isFinal() {
-        if (isPrimitive) return false;
+        if (isSpecial) return false;
         return el.getModifiers().contains(Modifier.FINAL);
     }
 
     @Override
     public boolean isInner() {
-        if (isPrimitive) return false;
+        if (isSpecial) return false;
         return (getDeclaringClass() != null) && !el.getModifiers().contains(Modifier.STATIC);
     }
 
     @Override
     public boolean isEnum() {
-        if (isPrimitive) return false;
+        if (isSpecial) return false;
         return el.getKind() == ElementKind.ENUM;
     }