diff options
author | Sven Gothel <[email protected]> | 2014-05-11 03:03:36 +0200 |
---|---|---|
committer | Sven Gothel <[email protected]> | 2014-05-11 03:03:36 +0200 |
commit | 1e53a38eb06aa8ff50660fdf7bd8570b27f27c56 (patch) | |
tree | f061dfb77af5b4c1f27da78b4dbd1881b400abc3 /src/java/com/jogamp/gluegen/JavaEmitter.java | |
parent | 598da96b3d2ffc3e0915f73749cbafa5fa5cea90 (diff) |
Bug 923: Remove dependency of CStruct annotation processor _generation_ and generated_class_user due to Java8 issues.
Java8's annotation processor as embedded within javac does not allow
referencing not-yet existing generated classes in a class source code
which will produce these generated classes via the annotation process.
Example:
+++
import com.jogamp.gluegen.structgen.CStruct;
public class Lala {
@CStruct(name="RenderingConfig", header="TestStruct01.h")
public RenderingConfig config;
}
+++
Above example illustrates that the type 'RenderingConfig'
does not exist at time of processing the annotation.
The type will be created via the annotation process itself.
Even though we pass '-proc:only', i.e. skip java compilation,
Java8's annotation processing via javac fails in such case.
We see this as a bug within javac's annotation processing itself!
+++
This workaround splits the annotation process and using the class as
generated by the former.
To allow this to work, CStruct receives a new field 'jname'
allowing to enforce the java-name of the structure
using a dummy field type like boolean.
@CStruct(name="RenderingConfig", jname="RenderingConfig", header="TestStruct01.h")
public boolean dummy;
Further more CStruct can be annotated on the package, i.e. 'package-info.java',
avoiding the dependency problem altogether.
To support multiple header files and types,
'CStructs' has been introduced using an array of 'CStruct'.
@CStructs({@CStruct(name="RenderingConfig", header="TestStruct01.h"), @CStruct(name="Pixel", header="TestStruct02.h")})
package com.jogamp.gluegen.test.junit.structgen;
Tests:
- Build w/ Java7 and Java8
- Validated 'major version 50' (Java 6) class files (OK)
Diffstat (limited to 'src/java/com/jogamp/gluegen/JavaEmitter.java')
-rw-r--r-- | src/java/com/jogamp/gluegen/JavaEmitter.java | 233 |
1 files changed, 118 insertions, 115 deletions
diff --git a/src/java/com/jogamp/gluegen/JavaEmitter.java b/src/java/com/jogamp/gluegen/JavaEmitter.java index ec8757c..3f4fa9e 100644 --- a/src/java/com/jogamp/gluegen/JavaEmitter.java +++ b/src/java/com/jogamp/gluegen/JavaEmitter.java @@ -836,69 +836,74 @@ public class JavaEmitter implements GlueEmitter { } } - String structClassPkg = cfg.packageForStruct(name); - PrintWriter writer = null; - PrintWriter newWriter = null; + final String structClassPkg = cfg.packageForStruct(name); + final PrintWriter javaWriter; + final PrintWriter jniWriter; try { - writer = openFile( - cfg.javaOutputDir() + File.separator + - CodeGenUtils.packageAsPath(structClassPkg) + - File.separator + containingTypeName + ".java", containingTypeName); - CodeGenUtils.emitAutogeneratedWarning(writer, this); - if (needsNativeCode) { - String nRoot = cfg.nativeOutputDir(); - if (cfg.nativeOutputUsesJavaHierarchy()) { - nRoot += File.separator + CodeGenUtils.packageAsPath(cfg.packageName()); + javaWriter = openFile(cfg.javaOutputDir() + File.separator + + CodeGenUtils.packageAsPath(structClassPkg) + + File.separator + containingTypeName + ".java", containingTypeName); + if( null == javaWriter ) { + // suppress output if openFile deliberately returns null. + return; + } + CodeGenUtils.emitAutogeneratedWarning(javaWriter, this); + if (needsNativeCode) { + String nRoot = cfg.nativeOutputDir(); + if (cfg.nativeOutputUsesJavaHierarchy()) { + nRoot += File.separator + CodeGenUtils.packageAsPath(cfg.packageName()); + } + jniWriter = openFile(nRoot + File.separator + containingTypeName + "_JNI.c", containingTypeName); + CodeGenUtils.emitAutogeneratedWarning(jniWriter, this); + emitCHeader(jniWriter, containingTypeName); + } else { + jniWriter = null; } - newWriter = openFile(nRoot + File.separator + containingTypeName + "_JNI.c", containingTypeName); - CodeGenUtils.emitAutogeneratedWarning(newWriter, this); - emitCHeader(newWriter, containingTypeName); - } } catch(Exception e) { - throw new RuntimeException("Unable to open files for emission of struct class", e); + throw new RuntimeException("Unable to open files for emission of struct class", e); } - writer.println(); - writer.println("package " + structClassPkg + ";"); - writer.println(); - writer.println("import java.nio.*;"); - writer.println(); + javaWriter.println(); + javaWriter.println("package " + structClassPkg + ";"); + javaWriter.println(); + javaWriter.println("import java.nio.*;"); + javaWriter.println(); - writer.println("import " + cfg.gluegenRuntimePackage() + ".*;"); - writer.println("import " + DynamicLookupHelper.class.getPackage().getName() + ".*;"); - writer.println("import " + Buffers.class.getPackage().getName() + ".*;"); - writer.println("import " + MachineDescriptionRuntime.class.getName() + ";"); - writer.println(); + javaWriter.println("import " + cfg.gluegenRuntimePackage() + ".*;"); + javaWriter.println("import " + DynamicLookupHelper.class.getPackage().getName() + ".*;"); + javaWriter.println("import " + Buffers.class.getPackage().getName() + ".*;"); + javaWriter.println("import " + MachineDescriptionRuntime.class.getName() + ";"); + javaWriter.println(); List<String> imports = cfg.imports(); for (String str : imports) { - writer.print("import "); - writer.print(str); - writer.println(";"); + javaWriter.print("import "); + javaWriter.print(str); + javaWriter.println(";"); } - writer.println(); + javaWriter.println(); List<String> javadoc = cfg.javadocForClass(containingTypeName); for (String doc : javadoc) { - writer.println(doc); + javaWriter.println(doc); } - writer.print("public class " + containingTypeName + " "); + javaWriter.print("public class " + containingTypeName + " "); boolean firstIteration = true; List<String> userSpecifiedInterfaces = cfg.implementedInterfaces(containingTypeName); for (String userInterface : userSpecifiedInterfaces) { if (firstIteration) { - writer.print("implements "); + javaWriter.print("implements "); } firstIteration = false; - writer.print(userInterface); - writer.print(" "); - } - writer.println("{"); - writer.println(); - writer.println(" StructAccessor accessor;"); - writer.println(); - writer.println(" private static final int mdIdx = MachineDescriptionRuntime.getStatic().ordinal();"); - writer.println(); + javaWriter.print(userInterface); + javaWriter.print(" "); + } + javaWriter.println("{"); + javaWriter.println(); + javaWriter.println(" StructAccessor accessor;"); + javaWriter.println(); + javaWriter.println(" private static final int mdIdx = MachineDescriptionRuntime.getStatic().ordinal();"); + javaWriter.println(); // generate all offset and size arrays - generateOffsetAndSizeArrays(writer, containingTypeName, structType, null); /* w/o offset */ + generateOffsetAndSizeArrays(javaWriter, containingTypeName, structType, null); /* w/o offset */ for (int i = 0; i < structType.getNumFields(); i++) { final Field field = structType.getField(i); final Type fieldType = field.getType(); @@ -917,14 +922,14 @@ public class JavaEmitter implements GlueEmitter { field + "\" in type \"" + name + "\")"); } - generateOffsetAndSizeArrays(writer, fieldName, fieldType, field); + generateOffsetAndSizeArrays(javaWriter, fieldName, fieldType, field); } else if (fieldType.isArray()) { Type baseElementType = field.getType().asArray().getBaseElementType(); if(!baseElementType.isPrimitive()) break; - generateOffsetAndSizeArrays(writer, fieldName, null, field); /* w/o size */ + generateOffsetAndSizeArrays(javaWriter, fieldName, null, field); /* w/o size */ } else { JavaType externalJavaType = null; try { @@ -936,7 +941,7 @@ public class JavaEmitter implements GlueEmitter { } if (externalJavaType.isPrimitive()) { // Primitive type - generateOffsetAndSizeArrays(writer, fieldName, null, field); /* w/o size */ + generateOffsetAndSizeArrays(javaWriter, fieldName, null, field); /* w/o size */ } else { // FIXME LOG.log(WARNING, "Complicated fields (field \"{0}\" of type \"{1}\") not implemented yet", new Object[]{field, name}); @@ -946,27 +951,27 @@ public class JavaEmitter implements GlueEmitter { } } } - writer.println(); - - writer.println(" public static int size() {"); - writer.println(" return "+containingTypeName+"_size[mdIdx];"); - writer.println(" }"); - writer.println(); - writer.println(" public static " + containingTypeName + " create() {"); - writer.println(" return create(Buffers.newDirectByteBuffer(size()));"); - writer.println(" }"); - writer.println(); - writer.println(" public static " + containingTypeName + " create(java.nio.ByteBuffer buf) {"); - writer.println(" return new " + containingTypeName + "(buf);"); - writer.println(" }"); - writer.println(); - writer.println(" " + containingTypeName + "(java.nio.ByteBuffer buf) {"); - writer.println(" accessor = new StructAccessor(buf);"); - writer.println(" }"); - writer.println(); - writer.println(" public java.nio.ByteBuffer getBuffer() {"); - writer.println(" return accessor.getBuffer();"); - writer.println(" }"); + javaWriter.println(); + + javaWriter.println(" public static int size() {"); + javaWriter.println(" return "+containingTypeName+"_size[mdIdx];"); + javaWriter.println(" }"); + javaWriter.println(); + javaWriter.println(" public static " + containingTypeName + " create() {"); + javaWriter.println(" return create(Buffers.newDirectByteBuffer(size()));"); + javaWriter.println(" }"); + javaWriter.println(); + javaWriter.println(" public static " + containingTypeName + " create(java.nio.ByteBuffer buf) {"); + javaWriter.println(" return new " + containingTypeName + "(buf);"); + javaWriter.println(" }"); + javaWriter.println(); + javaWriter.println(" " + containingTypeName + "(java.nio.ByteBuffer buf) {"); + javaWriter.println(" accessor = new StructAccessor(buf);"); + javaWriter.println(" }"); + javaWriter.println(); + javaWriter.println(" public java.nio.ByteBuffer getBuffer() {"); + javaWriter.println(" return accessor.getBuffer();"); + javaWriter.println(" }"); for (int i = 0; i < structType.getNumFields(); i++) { final Field field = structType.getField(i); @@ -983,12 +988,12 @@ public class JavaEmitter implements GlueEmitter { FunctionSymbol funcSym = new FunctionSymbol(fieldName, funcType); MethodBinding binding = bindFunction(funcSym, containingType, containingCType, machDescJava); binding.findThisPointer(); // FIXME: need to provide option to disable this on per-function basis - writer.println(); + javaWriter.println(); // Emit public Java entry point for calling this function pointer JavaMethodBindingEmitter emitter = new JavaMethodBindingEmitter(binding, - writer, + javaWriter, cfg.runtimeExceptionType(), cfg.unsupportedExceptionType(), true, @@ -1008,7 +1013,7 @@ public class JavaEmitter implements GlueEmitter { // Emit private native Java entry point for calling this function pointer emitter = new JavaMethodBindingEmitter(binding, - writer, + javaWriter, cfg.runtimeExceptionType(), cfg.unsupportedExceptionType(), false, @@ -1029,7 +1034,7 @@ public class JavaEmitter implements GlueEmitter { // Emit (private) C entry point for calling this function pointer CMethodBindingEmitter cEmitter = new CMethodBindingEmitter(binding, - newWriter, + jniWriter, structClassPkg, containingTypeName, true, // FIXME: this is optional at this point @@ -1052,12 +1057,12 @@ public class JavaEmitter implements GlueEmitter { field + "\" in type \"" + name + "\")"); } - writer.println(); - generateGetterSignature(writer, false, fieldType.getName(), capitalizeString(fieldName)); - writer.println(" {"); - writer.println(" return " + fieldType.getName() + ".create( accessor.slice( " + + javaWriter.println(); + generateGetterSignature(javaWriter, false, fieldType.getName(), capitalizeString(fieldName)); + javaWriter.println(" {"); + javaWriter.println(" return " + fieldType.getName() + ".create( accessor.slice( " + fieldName+"_offset[mdIdx], "+fieldName+"_size[mdIdx] ) );"); - writer.println(" }"); + javaWriter.println(" }"); } else if (fieldType.isArray()) { @@ -1070,18 +1075,18 @@ public class JavaEmitter implements GlueEmitter { String capitalized = capitalizeString(fieldName); // Setter - writer.println(); - generateSetterSignature(writer, false, containingTypeName, capitalized, paramType+"[]"); - writer.println(" {"); - writer.print (" accessor.set" + capitalizeString(paramType) + "sAt(" + fieldName+"_offset[mdIdx], val);"); - writer.println(" return this;"); - writer.println(" }"); - writer.println(); + javaWriter.println(); + generateSetterSignature(javaWriter, false, containingTypeName, capitalized, paramType+"[]"); + javaWriter.println(" {"); + javaWriter.print (" accessor.set" + capitalizeString(paramType) + "sAt(" + fieldName+"_offset[mdIdx], val);"); + javaWriter.println(" return this;"); + javaWriter.println(" }"); + javaWriter.println(); // Getter - generateGetterSignature(writer, false, paramType+"[]", capitalized); - writer.println(" {"); - writer.print (" return accessor.get" + capitalizeString(paramType) + "sAt(" + fieldName+"_offset[mdIdx], new " +paramType+"["+fieldType.asArray().getLength()+"]);"); - writer.println(" }"); + generateGetterSignature(javaWriter, false, paramType+"[]", capitalized); + javaWriter.println(" {"); + javaWriter.print (" return accessor.get" + capitalizeString(paramType) + "sAt(" + fieldName+"_offset[mdIdx], new " +paramType+"["+fieldType.asArray().getLength()+"]);"); + javaWriter.println(" }"); } else { JavaType javaType = null; @@ -1111,40 +1116,40 @@ public class JavaEmitter implements GlueEmitter { ", sizeDenominator "+sizeDenominator); } - writer.println(); + javaWriter.println(); // Setter - generateSetterSignature(writer, false, containingTypeName, capFieldName, javaTypeName); - writer.println(" {"); + generateSetterSignature(javaWriter, false, containingTypeName, capFieldName, javaTypeName); + javaWriter.println(" {"); if( fieldTypeNativeSizeFixed ) { - writer.println(" accessor.set" + capJavaTypeName + "At(" + fieldName+"_offset[mdIdx], val);"); + javaWriter.println(" accessor.set" + capJavaTypeName + "At(" + fieldName+"_offset[mdIdx], val);"); } else { - writer.println(" accessor.set" + capJavaTypeName + "At(" + fieldName+"_offset[mdIdx], val, MachineDescriptionRuntime.getStatic().md."+sizeDenominator+"SizeInBytes());"); + javaWriter.println(" accessor.set" + capJavaTypeName + "At(" + fieldName+"_offset[mdIdx], val, MachineDescriptionRuntime.getStatic().md."+sizeDenominator+"SizeInBytes());"); } - writer.println(" return this;"); - writer.println(" }"); - writer.println(); + javaWriter.println(" return this;"); + javaWriter.println(" }"); + javaWriter.println(); // Getter - generateGetterSignature(writer, false, javaTypeName, capFieldName); - writer.println(" {"); - writer.print (" return "); + generateGetterSignature(javaWriter, false, javaTypeName, capFieldName); + javaWriter.println(" {"); + javaWriter.print (" return "); if( fieldTypeNativeSizeFixed ) { - writer.println("accessor.get" + capJavaTypeName + "At(" + fieldName+"_offset[mdIdx]);"); + javaWriter.println("accessor.get" + capJavaTypeName + "At(" + fieldName+"_offset[mdIdx]);"); } else { - writer.println("accessor.get" + capJavaTypeName + "At(" + fieldName+"_offset[mdIdx], MachineDescriptionRuntime.getStatic().md."+sizeDenominator+"SizeInBytes());"); + javaWriter.println("accessor.get" + capJavaTypeName + "At(" + fieldName+"_offset[mdIdx], MachineDescriptionRuntime.getStatic().md."+sizeDenominator+"SizeInBytes());"); } - writer.println(" }"); + javaWriter.println(" }"); } } } } - emitCustomJavaCode(writer, containingTypeName); - writer.println("}"); - writer.flush(); - writer.close(); + emitCustomJavaCode(javaWriter, containingTypeName); + javaWriter.println("}"); + javaWriter.flush(); + javaWriter.close(); if (needsNativeCode) { - newWriter.flush(); - newWriter.close(); + jniWriter.flush(); + jniWriter.close(); } } @Override @@ -1415,17 +1420,15 @@ public class JavaEmitter implements GlueEmitter { /** * @param filename the class's full filename to open w/ write access * @param simpleClassName the simple class name, i.e. w/o package name - * @return a {@link PrintWriter} instance to write the class source file + * @return a {@link PrintWriter} instance to write the class source file or <code>null</code> to suppress output! * @throws IOException */ protected PrintWriter openFile(String filename, String simpleClassName) throws IOException { //System.out.println("Trying to open: " + filename); - File file = new File(filename); - String parentDir = file.getParent(); - if (parentDir != null) - { - File pDirFile = new File(parentDir); - pDirFile.mkdirs(); + final File file = new File(filename); + final String parentDir = file.getParent(); + if (parentDir != null) { + new File(parentDir).mkdirs(); } return new PrintWriter(new BufferedWriter(new FileWriter(file))); } |