< prev index next > src/jdk.compiler/share/classes/com/sun/tools/javac/jvm/ClassWriter.java
Print this page
import javax.tools.JavaFileObject;
import com.sun.tools.javac.code.*;
import com.sun.tools.javac.code.Attribute.RetentionPolicy;
import com.sun.tools.javac.code.Directive.*;
+ import com.sun.tools.javac.code.Scope.WriteableScope;
+ import com.sun.tools.javac.code.Source.Feature;
import com.sun.tools.javac.code.Symbol.*;
import com.sun.tools.javac.code.Type.*;
import com.sun.tools.javac.code.Types.SignatureGenerator.InvalidSignatureException;
import com.sun.tools.javac.comp.Check;
import com.sun.tools.javac.file.PathFileObject;
/** Type utilities. */
private Types types;
private Check check;
+ private boolean allowPrimitiveClasses;
+
/**
* If true, class files will be written in module-specific subdirectories
* of the CLASS_OUTPUT location.
*/
public boolean multiModuleMode;
private final Log log;
/** The name table. */
private final Names names;
+ private final Symtab syms;
+
/** Access to files. */
private final JavaFileManager fileManager;
/** The tags and constants used in compressed stackmap. */
static final int SAME_FRAME_SIZE = 64;
source = Source.instance(context);
types = Types.instance(context);
check = Check.instance(context);
fileManager = context.get(JavaFileManager.class);
poolWriter = Gen.instance(context).poolWriter;
+ syms = Symtab.instance(context);
verbose = options.isSet(VERBOSE);
genCrt = options.isSet(XJCOV);
debugstackmap = options.isSet("debug.stackmap");
dumpClassModifiers = modifierFlags.indexOf('c') != -1;
dumpFieldModifiers = modifierFlags.indexOf('f') != -1;
dumpInnerClassModifiers = modifierFlags.indexOf('i') != -1;
dumpMethodModifiers = modifierFlags.indexOf('m') != -1;
}
+ Source source = Source.instance(context);
+ allowPrimitiveClasses = Feature.PRIMITIVE_CLASSES.allowedInSource(source) && options.isSet("enablePrimitiveClasses");
}
public void addExtraAttributes(ToIntFunction<Symbol> addExtraAttributes) {
extraAttributeHooks = extraAttributeHooks.prepend(addExtraAttributes);
}
return sbuf.toString();
}
//where
private static final String[] flagName = {
"PUBLIC", "PRIVATE", "PROTECTED", "STATIC", "FINAL",
! "SUPER", "VOLATILE", "TRANSIENT", "NATIVE", "INTERFACE",
"ABSTRACT", "STRICTFP"};
/******************************************************************
* Output routines
******************************************************************/
return sbuf.toString();
}
//where
private static final String[] flagName = {
"PUBLIC", "PRIVATE", "PROTECTED", "STATIC", "FINAL",
! "IDENTITY", "VOLATILE", "TRANSIENT", "NATIVE", "INTERFACE",
"ABSTRACT", "STRICTFP"};
/******************************************************************
* Output routines
******************************************************************/
databuf.appendChar(poolWriter.innerClasses.size());
for (ClassSymbol inner : poolWriter.innerClasses) {
inner.markAbstractIfNeeded(types);
int flags = adjustFlags(inner.flags_field);
if ((flags & INTERFACE) != 0) flags |= ABSTRACT; // Interfaces are always ABSTRACT
- flags &= ~STRICTFP; //inner classes should not have the strictfp flag set.
if (dumpInnerClassModifiers) {
PrintWriter pw = log.getWriter(Log.WriterKind.ERROR);
pw.println("INNERCLASS " + inner.name);
pw.println("---" + flagNames(flags));
}
databuf.appendChar(flags);
}
endAttr(alenIdx);
}
+ /** Write out "Preload" attribute by enumerating the value classes encountered in field/method descriptors during this compilation.
+ */
+ void writePreloadAttribute() {
+ int alenIdx = writeAttr(names.Preload);
+ databuf.appendChar(poolWriter.preloadClasses.size());
+ for (ClassSymbol c : poolWriter.preloadClasses) {
+ databuf.appendChar(poolWriter.putClass(c));
+ }
+ endAttr(alenIdx);
+ }
+
int writeRecordAttribute(ClassSymbol csym) {
int alenIdx = writeAttr(names.Record);
Scope s = csym.members();
databuf.appendChar(csym.getRecordComponents().size());
for (VarSymbol v: csym.getRecordComponents()) {
pw.println("FIELD " + v.name);
pw.println("---" + flagNames(v.flags()));
}
databuf.appendChar(poolWriter.putName(v.name));
databuf.appendChar(poolWriter.putDescriptor(v));
+ Type fldType = v.erasure(types);
+ if (fldType.requiresPreload(v.owner)) {
+ poolWriter.enterPreloadClass((ClassSymbol) fldType.tsym);
+ }
int acountIdx = beginAttrs();
int acount = 0;
if (v.getConstValue() != null) {
int alenIdx = writeAttr(names.ConstantValue);
databuf.appendChar(poolWriter.putConstant(v.getConstValue()));
pw.println("METHOD " + m.name);
pw.println("---" + flagNames(m.flags()));
}
databuf.appendChar(poolWriter.putName(m.name));
databuf.appendChar(poolWriter.putDescriptor(m));
+ MethodType mtype = (MethodType) m.externalType(types);
+ for (Type t : mtype.getParameterTypes()) {
+ if (t.requiresPreload(m.owner)) {
+ poolWriter.enterPreloadClass((ClassSymbol) t.tsym);
+ }
+ }
+ Type returnType = mtype.getReturnType();
+ if (returnType.requiresPreload(m.owner)) {
+ poolWriter.enterPreloadClass((ClassSymbol) returnType.tsym);
+ }
int acountIdx = beginAttrs();
int acount = 0;
if (m.code != null) {
int alenIdx = writeAttr(names.Code);
writeCode(m.code);
}
private boolean requiresParamNames(MethodSymbol m) {
if (options.isSet(PARAMETERS))
return true;
! if (m.isConstructor() && (m.flags_field & RECORD) != 0)
return true;
return false;
}
private boolean requiresParamFlags(MethodSymbol m) {
}
private boolean requiresParamNames(MethodSymbol m) {
if (options.isSet(PARAMETERS))
return true;
! if ((m.isInitOrVNew() || m.isValueObjectFactory()) && (m.flags_field & RECORD) != 0)
return true;
return false;
}
private boolean requiresParamFlags(MethodSymbol m) {
if (debugstackmap) System.out.print("null");
databuf.appendByte(5);
break;
case CLASS:
case ARRAY:
+ if (debugstackmap) System.out.print("object(" + types.erasure(t).tsym + ")");
+ databuf.appendByte(7);
+ databuf.appendChar(allowPrimitiveClasses && t.isPrimitiveClass() ? poolWriter.putClass(new ConstantPoolQType(types.erasure(t), types)) : poolWriter.putClass(types.erasure(t)));
+ break;
case TYPEVAR:
if (debugstackmap) System.out.print("object(" + types.erasure(t).tsym + ")");
databuf.appendByte(7);
databuf.appendChar(poolWriter.putClass(types.erasure(t)));
break;
int flags;
if (c.owner.kind == MDL) {
flags = ACC_MODULE;
} else {
! flags = adjustFlags(c.flags() & ~DEFAULT);
if ((flags & PROTECTED) != 0) flags |= PUBLIC;
! flags = flags & ClassFlags & ~STRICTFP;
- if ((flags & INTERFACE) == 0) flags |= ACC_SUPER;
}
if (dumpClassModifiers) {
PrintWriter pw = log.getWriter(Log.WriterKind.ERROR);
pw.println();
int flags;
if (c.owner.kind == MDL) {
flags = ACC_MODULE;
} else {
! flags = adjustFlags(c.flags() & ~(DEFAULT | STRICTFP));
if ((flags & PROTECTED) != 0) flags |= PUBLIC;
! flags = flags & AdjustedClassFlags;
}
if (dumpClassModifiers) {
PrintWriter pw = log.getWriter(Log.WriterKind.ERROR);
pw.println();
for (Symbol sym : c.members().getSymbols(NON_RECURSIVE)) {
switch (sym.kind) {
case VAR: fieldsCount++; break;
case MTH: if ((sym.flags() & HYPOTHETICAL) == 0) methodsCount++;
break;
! case TYP: poolWriter.enterInner((ClassSymbol)sym); break;
default : Assert.error();
}
}
if (c.trans_local != null) {
for (ClassSymbol local : c.trans_local) {
! poolWriter.enterInner(local);
}
}
databuf.appendChar(fieldsCount);
writeFields(c.members());
for (Symbol sym : c.members().getSymbols(NON_RECURSIVE)) {
switch (sym.kind) {
case VAR: fieldsCount++; break;
case MTH: if ((sym.flags() & HYPOTHETICAL) == 0) methodsCount++;
break;
! case TYP: poolWriter.enterInnerClass((ClassSymbol)sym); break;
default : Assert.error();
}
}
if (c.trans_local != null) {
for (ClassSymbol local : c.trans_local) {
! poolWriter.enterInnerClass(local);
}
}
databuf.appendChar(fieldsCount);
writeFields(c.members());
if (!poolWriter.innerClasses.isEmpty()) {
writeInnerClasses();
acount++;
}
+ if (!poolWriter.preloadClasses.isEmpty()) {
+ writePreloadAttribute();
+ acount++;
+ }
+
endAttrs(acountIdx, acount);
out.write(poolbuf.elems, 0, poolbuf.length);
poolWriter.writePool(out);
result |= ACC_BRIDGE;
if ((flags & VARARGS) != 0)
result |= ACC_VARARGS;
if ((flags & DEFAULT) != 0)
result &= ~ABSTRACT;
+ if ((flags & PRIMITIVE_CLASS) != 0)
+ result |= ACC_PRIMITIVE;
+ if ((flags & VALUE_CLASS) != 0)
+ result |= ACC_VALUE;
+ if ((flags & IDENTITY_TYPE) != 0)
+ result |= ACC_IDENTITY;
return result;
}
long getLastModified(FileObject filename) {
long mod = 0;
< prev index next >