use of org.eclipse.ceylon.langtools.tools.javac.util.JCDiagnostic.DiagnosticPosition in project ceylon by eclipse.
the class Attr method attribLazyConstantValue.
/**
* Attribute a "lazy constant value".
* @param env The env for the const value
* @param initializer The initializer for the const value
* @param type The expected type, or null
* @see VarSymbol#setLazyConstValue
*/
public Object attribLazyConstantValue(Env<AttrContext> env, JCVariableDecl variable, Type type) {
DiagnosticPosition prevLintPos = deferredLintHandler.setPos(variable.pos());
try {
// Use null as symbol to not attach the type annotation to any symbol.
// The initializer will later also be visited and then we'll attach
// to the symbol.
// This prevents having multiple type annotations, just because of
// lazy constant value evaluation.
memberEnter.typeAnnotate(variable.init, env, null, variable.pos());
annotate.flush();
Type itype = attribExpr(variable.init, env, type);
if (itype.constValue() != null) {
return coerce(itype, type).constValue();
} else {
return null;
}
} finally {
deferredLintHandler.setPos(prevLintPos);
}
}
use of org.eclipse.ceylon.langtools.tools.javac.util.JCDiagnostic.DiagnosticPosition in project ceylon by eclipse.
the class Attr method visitNewClass.
public void visitNewClass(final JCNewClass tree) {
Type owntype = types.createErrorType(tree.type);
// The local environment of a class creation is
// a new environment nested in the current one.
Env<AttrContext> localEnv = env.dup(tree, env.info.dup());
// The anonymous inner class definition of the new expression,
// if one is defined by it.
JCClassDecl cdef = tree.def;
// If enclosing class is given, attribute it, and
// complete class name to be fully qualified
// Class field following new
JCExpression clazz = tree.clazz;
// Identifier in class field
JCExpression clazzid;
// Annotated type enclosing clazzid
JCAnnotatedType annoclazzid;
annoclazzid = null;
if (clazz.hasTag(TYPEAPPLY)) {
clazzid = ((JCTypeApply) clazz).clazz;
if (clazzid.hasTag(ANNOTATED_TYPE)) {
annoclazzid = (JCAnnotatedType) clazzid;
clazzid = annoclazzid.underlyingType;
}
} else {
if (clazz.hasTag(ANNOTATED_TYPE)) {
annoclazzid = (JCAnnotatedType) clazz;
clazzid = annoclazzid.underlyingType;
} else {
clazzid = clazz;
}
}
// The same in fully qualified form
JCExpression clazzid1 = clazzid;
if (tree.encl != null) {
// We are seeing a qualified new, of the form
// <expr>.new C <...> (...) ...
// In this case, we let clazz stand for the name of the
// allocated class C prefixed with the type of the qualifier
// expression, so that we can
// resolve it with standard techniques later. I.e., if
// <expr> has type T, then <expr>.new C <...> (...)
// yields a clazz T.C.
Type encltype = chk.checkRefType(tree.encl.pos(), attribExpr(tree.encl, env));
// TODO 308: in <expr>.new C, do we also want to add the type annotations
// from expr to the combined type, or not? Yes, do this.
clazzid1 = make.at(clazz.pos).Select(make.Type(encltype), ((JCIdent) clazzid).name);
EndPosTable endPosTable = this.env.toplevel.endPositions;
endPosTable.storeEnd(clazzid1, tree.getEndPosition(endPosTable));
if (clazz.hasTag(ANNOTATED_TYPE)) {
JCAnnotatedType annoType = (JCAnnotatedType) clazz;
List<JCAnnotation> annos = annoType.annotations;
if (annoType.underlyingType.hasTag(TYPEAPPLY)) {
clazzid1 = make.at(tree.pos).TypeApply(clazzid1, ((JCTypeApply) clazz).arguments);
}
clazzid1 = make.at(tree.pos).AnnotatedType(annos, clazzid1);
} else if (clazz.hasTag(TYPEAPPLY)) {
clazzid1 = make.at(tree.pos).TypeApply(clazzid1, ((JCTypeApply) clazz).arguments);
}
clazz = clazzid1;
}
// Attribute clazz expression and store
// symbol + type back into the attributed tree.
Type clazztype = TreeInfo.isEnumInit(env.tree) ? attribIdentAsEnumType(env, (JCIdent) clazz) : attribType(clazz, env);
clazztype = chk.checkDiamond(tree, clazztype);
chk.validate(clazz, localEnv);
if (tree.encl != null) {
// We have to work in this case to store
// symbol + type back into the attributed tree.
tree.clazz.type = clazztype;
TreeInfo.setSymbol(clazzid, TreeInfo.symbol(clazzid1));
clazzid.type = ((JCIdent) clazzid).sym.type;
if (annoclazzid != null) {
annoclazzid.type = clazzid.type;
}
if (!clazztype.isErroneous()) {
if (cdef != null && clazztype.tsym.isInterface()) {
log.error(tree.encl.pos(), "anon.class.impl.intf.no.qual.for.new");
} else if (clazztype.tsym.isStatic()) {
log.error(tree.encl.pos(), "qualified.new.of.static.class", clazztype.tsym);
}
}
} else if (!clazztype.tsym.isInterface() && clazztype.getEnclosingType().hasTag(CLASS)) {
// Check for the existence of an apropos outer instance
rs.resolveImplicitThis(tree.pos(), env, clazztype);
}
// Attribute constructor arguments.
ListBuffer<Type> argtypesBuf = new ListBuffer<>();
int pkind = attribArgs(VAL, tree.args, localEnv, argtypesBuf);
List<Type> argtypes = argtypesBuf.toList();
List<Type> typeargtypes = attribTypes(tree.typeargs, localEnv);
// If we have made no mistakes in the class type...
if (clazztype.hasTag(CLASS)) {
// Enums may not be instantiated except implicitly
if (allowEnums && (clazztype.tsym.flags_field & Flags.ENUM) != 0 && (!env.tree.hasTag(VARDEF) || (((JCVariableDecl) env.tree).mods.flags & Flags.ENUM) == 0 || ((JCVariableDecl) env.tree).init != tree))
log.error(tree.pos(), "enum.cant.be.instantiated");
// Check that class is not abstract
if (cdef == null && (clazztype.tsym.flags() & (ABSTRACT | INTERFACE)) != 0) {
log.error(tree.pos(), "abstract.cant.be.instantiated", clazztype.tsym);
} else if (cdef != null && clazztype.tsym.isInterface()) {
// anonymous classes implementing an interface
if (!argtypes.isEmpty())
log.error(tree.args.head.pos(), "anon.class.impl.intf.no.args");
if (!typeargtypes.isEmpty())
log.error(tree.typeargs.head.pos(), "anon.class.impl.intf.no.typeargs");
// Error recovery: pretend no arguments were supplied.
argtypes = List.nil();
typeargtypes = List.nil();
} else if (TreeInfo.isDiamond(tree)) {
ClassType site = new ClassType(clazztype.getEnclosingType(), clazztype.tsym.type.getTypeArguments(), clazztype.tsym);
Env<AttrContext> diamondEnv = localEnv.dup(tree);
diamondEnv.info.selectSuper = cdef != null;
diamondEnv.info.pendingResolutionPhase = null;
// if the type of the instance creation expression is a class type
// apply method resolution inference (JLS 15.12.2.7). The return type
// of the resolved constructor will be a partially instantiated type
Symbol constructor = rs.resolveDiamond(tree.pos(), diamondEnv, site, argtypes, typeargtypes);
tree.constructor = constructor.baseSymbol();
final TypeSymbol csym = clazztype.tsym;
ResultInfo diamondResult = new ResultInfo(pkind, newMethodTemplate(resultInfo.pt, argtypes, typeargtypes), new Check.NestedCheckContext(resultInfo.checkContext) {
@Override
public void report(DiagnosticPosition _unused, JCDiagnostic details) {
enclosingContext.report(tree.clazz, diags.fragment("cant.apply.diamond.1", diags.fragment("diamond", csym), details));
}
});
Type constructorType = tree.constructorType = types.createErrorType(clazztype);
constructorType = checkId(noCheckTree, site, constructor, diamondEnv, diamondResult);
tree.clazz.type = types.createErrorType(clazztype);
if (!constructorType.isErroneous()) {
tree.clazz.type = clazztype = constructorType.getReturnType();
tree.constructorType = types.createMethodTypeWithReturn(constructorType, syms.voidType);
}
clazztype = chk.checkClassType(tree.clazz, tree.clazz.type, true);
} else // Resolve the called constructor under the assumption
// that we are referring to a superclass instance of the
// current instance (JLS ???).
{
// the following code alters some of the fields in the current
// AttrContext - hence, the current context must be dup'ed in
// order to avoid downstream failures
Env<AttrContext> rsEnv = localEnv.dup(tree);
rsEnv.info.selectSuper = cdef != null;
rsEnv.info.pendingResolutionPhase = null;
tree.constructor = rs.resolveConstructor(tree.pos(), rsEnv, clazztype, argtypes, typeargtypes);
if (cdef == null) {
// do not check twice!
tree.constructorType = checkId(noCheckTree, clazztype, tree.constructor, rsEnv, new ResultInfo(pkind, newMethodTemplate(syms.voidType, argtypes, typeargtypes)));
if (rsEnv.info.lastResolveVarargs())
Assert.check(tree.constructorType.isErroneous() || tree.varargsElement != null);
}
if (cdef == null && !clazztype.isErroneous() && clazztype.getTypeArguments().nonEmpty() && findDiamonds) {
findDiamond(localEnv, tree, clazztype);
}
}
if (cdef != null) {
// }
if (Resolve.isStatic(env))
cdef.mods.flags |= STATIC;
if (clazztype.tsym.isInterface()) {
cdef.implementing = List.of(clazz);
} else {
cdef.extending = clazz;
}
if (resultInfo.checkContext.deferredAttrContext().mode == DeferredAttr.AttrMode.CHECK && isSerializable(clazztype)) {
localEnv.info.isSerializable = true;
}
attribStat(cdef, localEnv);
checkLambdaCandidate(tree, cdef.sym, clazztype);
// and delete it from the new expression
if (tree.encl != null && !clazztype.tsym.isInterface()) {
tree.args = tree.args.prepend(makeNullCheck(tree.encl));
argtypes = argtypes.prepend(tree.encl.type);
tree.encl = null;
}
// Reassign clazztype and recompute constructor.
clazztype = cdef.sym.type;
Symbol sym = tree.constructor = rs.resolveConstructor(tree.pos(), localEnv, clazztype, argtypes, typeargtypes);
Assert.check(sym.kind < AMBIGUOUS);
tree.constructor = sym;
tree.constructorType = checkId(noCheckTree, clazztype, tree.constructor, localEnv, new ResultInfo(pkind, newMethodTemplate(syms.voidType, argtypes, typeargtypes)));
}
if (tree.constructor != null && tree.constructor.kind == MTH)
owntype = clazztype;
}
result = check(tree, owntype, VAL, resultInfo);
InferenceContext inferenceContext = resultInfo.checkContext.inferenceContext();
if (tree.constructorType != null && inferenceContext.free(tree.constructorType)) {
// we need to wait for inference to finish and then replace inference vars in the constructor type
inferenceContext.addFreeTypeListener(List.of(tree.constructorType), new FreeTypeListener() {
@Override
public void typesInferred(InferenceContext instantiatedContext) {
tree.constructorType = instantiatedContext.asInstType(tree.constructorType);
}
});
}
chk.validate(tree.typeargs, localEnv);
}
use of org.eclipse.ceylon.langtools.tools.javac.util.JCDiagnostic.DiagnosticPosition in project ceylon by eclipse.
the class DeferredLintHandler method setPos.
/**
*Sets the current position to the provided {@code currentPos}. {@link LintLogger}s
* passed to subsequent invocations of {@link #report(LintLogger) } will be associated
* with the given position.
*/
public DiagnosticPosition setPos(DiagnosticPosition currentPos) {
DiagnosticPosition prevPosition = this.currentPos;
this.currentPos = currentPos;
return prevPosition;
}
Aggregations