use of com.redhat.ceylon.compiler.typechecker.tree.Tree.Expression in project ceylon-compiler by ceylon.
the class StatementTransformer method transformCaseMatch.
private JCStatement transformCaseMatch(Naming.SyntheticName selectorAlias, Tree.SwitchClause switchClause, Tree.CaseClause caseClause, String tmpVar, Tree.Term outerExpression, Type expectedType, Tree.MatchCase matchCase, JCStatement last, Type switchType, boolean primitiveSelector) {
at(matchCase);
JCExpression tests = null;
java.util.List<Tree.Expression> expressions = matchCase.getExpressionList().getExpressions();
for (Tree.Expression expr : expressions) {
Tree.Term term = ExpressionTransformer.eliminateParens(expr.getTerm());
boolean unboxedEquality = primitiveSelector || isCeylonBasicType(typeFact().getDefiniteType(switchType));
JCExpression transformedExpression = expressionGen().transformExpression(term, unboxedEquality ? BoxingStrategy.UNBOXED : BoxingStrategy.BOXED, term.getTypeModel());
JCExpression test;
if (term instanceof Tree.Literal || term instanceof Tree.NegativeOp) {
if (unboxedEquality) {
if (term instanceof Tree.StringLiteral) {
test = make().Apply(null, makeSelect(unboxType(selectorAlias.makeIdent(), term.getTypeModel()), "equals"), List.<JCExpression>of(transformedExpression));
} else {
test = make().Binary(JCTree.EQ, primitiveSelector ? selectorAlias.makeIdent() : unboxType(selectorAlias.makeIdent(), term.getTypeModel()), transformedExpression);
}
} else {
test = make().Apply(null, makeSelect(selectorAlias.makeIdent(), "equals"), List.<JCExpression>of(transformedExpression));
}
if (isOptional(switchType)) {
test = make().Binary(JCTree.AND, make().Binary(JCTree.NE, selectorAlias.makeIdent(), makeNull()), test);
}
} else {
JCExpression selectorExpr;
if (!primitiveSelector && isCeylonBasicType(typeFact().getDefiniteType(switchType))) {
selectorExpr = unboxType(selectorAlias.makeIdent(), term.getTypeModel());
} else {
selectorExpr = selectorAlias.makeIdent();
}
test = make().Binary(JCTree.EQ, selectorExpr, transformedExpression);
}
if (tests == null)
tests = test;
else if (isNull(term.getTypeModel())) {
// ensure we do any null check as the first operation in the ||-ed expression
tests = make().Binary(JCTree.OR, test, tests);
} else {
tests = make().Binary(JCTree.OR, tests, test);
}
}
Substitution prevSubst = null;
if (switchClause.getSwitched().getVariable() != null) {
// Prepare for variable substitution in the following code block
prevSubst = naming.addVariableSubst(switchClause.getSwitched().getVariable().getDeclarationModel(), selectorAlias.toString());
}
JCBlock block = transformCaseClauseBlock(caseClause, tmpVar, outerExpression, expectedType);
if (prevSubst != null) {
// Deactivate the above variable substitution
prevSubst.close();
}
return at(caseClause).If(tests, block, last);
}
use of com.redhat.ceylon.compiler.typechecker.tree.Tree.Expression in project ceylon-compiler by ceylon.
the class MethodOrValueReferenceVisitor method visit.
@Override
public void visit(Tree.ForComprehensionClause that) {
super.visit(that);
final SpecifierExpression specifier = that.getForIterator().getSpecifierExpression();
if (specifier != null) {
final Expression expr = specifier.getExpression();
final Term term = expr.getTerm();
if (term instanceof Tree.Primary) {
capture((Tree.Primary) term, true);
}
}
that.getComprehensionClause().visit(this);
}
use of com.redhat.ceylon.compiler.typechecker.tree.Tree.Expression in project ceylon-compiler by ceylon.
the class CeylonDocTool method warningMissingThrows.
protected void warningMissingThrows(Declaration d) {
if (ignoreMissingThrows) {
return;
}
final Scope scope = d.getScope();
final PhasedUnit unit = getUnit(d);
final Node node = getNode(d);
if (scope == null || unit == null || unit.getUnit() == null || node == null || !(d instanceof FunctionOrValue)) {
return;
}
List<Type> documentedExceptions = new ArrayList<Type>();
for (Annotation annotation : d.getAnnotations()) {
if (annotation.getName().equals("throws")) {
String exceptionName = annotation.getPositionalArguments().get(0);
Declaration exceptionDecl = scope.getMemberOrParameter(unit.getUnit(), exceptionName, null, false);
if (exceptionDecl instanceof TypeDeclaration) {
documentedExceptions.add(((TypeDeclaration) exceptionDecl).getType());
}
}
}
final List<Type> thrownExceptions = new ArrayList<Type>();
node.visitChildren(new Visitor() {
@Override
public void visit(Tree.Throw that) {
Expression expression = that.getExpression();
if (expression != null) {
thrownExceptions.add(expression.getTypeModel());
} else {
thrownExceptions.add(unit.getUnit().getExceptionType());
}
}
@Override
public void visit(Tree.Declaration that) {
// the end of searching
}
});
for (Type thrownException : thrownExceptions) {
boolean isDocumented = false;
for (Type documentedException : documentedExceptions) {
if (thrownException.isSubtypeOf(documentedException)) {
isDocumented = true;
break;
}
}
if (!isDocumented) {
log.warning(CeylondMessages.msg("warn.missingThrows", thrownException.asString(), getWhere(d), getPosition(getNode(d))));
}
}
}
use of com.redhat.ceylon.compiler.typechecker.tree.Tree.Expression in project ceylon-compiler by ceylon.
the class StatementTransformer method transform.
JCStatement transform(Node node, Tree.SwitchClause switchClause, Tree.SwitchCaseList caseList, String tmpVar, Tree.Term outerExpression, Type expectedType) {
at(switchClause);
block();
SwitchTransformation transformation = null;
Type exprType = switchExpressionType(switchClause);
Boolean switchUnboxed = switchExpressionUnboxed(switchClause);
// Are we switching with just String literal or Character literal match cases?
if (isJavaSwitchableType(exprType, switchUnboxed)) {
boolean canUseSwitch = true;
caseStmts: for (Tree.CaseClause clause : caseList.getCaseClauses()) {
if (clause.getCaseItem() instanceof Tree.MatchCase) {
java.util.List<Expression> caseExprs = ((Tree.MatchCase) clause.getCaseItem()).getExpressionList().getExpressions();
caseExpr: for (Tree.Expression expr : caseExprs) {
Tree.Term e = ExpressionTransformer.eliminateParens(expr);
if (e instanceof Tree.StringLiteral || e instanceof Tree.CharLiteral) {
continue caseExpr;
} else if (e instanceof Tree.BaseMemberExpression && ((Tree.BaseMemberExpression) e).getDeclaration() instanceof Value && ((Value) ((Tree.BaseMemberExpression) e).getDeclaration()).isEnumValue()) {
continue caseExpr;
} else {
canUseSwitch = false;
break caseStmts;
}
}
} else {
canUseSwitch = false;
break caseStmts;
}
}
if (canUseSwitch) {
// yes, so use a Java Switch
transformation = new Switch();
}
}
if (transformation == null && isOptional(exprType)) {
// Are we switching with just String literal or Character literal plus null
// match cases?
Type definiteType = typeFact().getDefiniteType(exprType);
if (isJavaSwitchableType(definiteType, switchUnboxed)) {
boolean canUseIfElseSwitch = true;
boolean hasSingletonNullCase = false;
caseStmts: for (Tree.CaseClause clause : caseList.getCaseClauses()) {
if (clause.getCaseItem() instanceof Tree.MatchCase) {
if (getSingletonNullCase(clause) != null) {
hasSingletonNullCase = true;
}
java.util.List<Expression> caseExprs = ((Tree.MatchCase) clause.getCaseItem()).getExpressionList().getExpressions();
caseExpr: for (Tree.Expression expr : caseExprs) {
Tree.Term e = ExpressionTransformer.eliminateParens(expr);
if (e instanceof Tree.StringLiteral || e instanceof Tree.CharLiteral) {
continue caseExpr;
} else if (e instanceof Tree.BaseMemberExpression && isNullValue(((Tree.BaseMemberExpression) e).getDeclaration()) && caseExprs.size() == 1) {
continue caseExpr;
} else if (e instanceof Tree.BaseMemberExpression && ((Tree.BaseMemberExpression) e).getDeclaration() instanceof Value && ((Value) ((Tree.BaseMemberExpression) e).getDeclaration()).isEnumValue()) {
continue caseExpr;
} else {
canUseIfElseSwitch = false;
break caseStmts;
}
}
} else {
canUseIfElseSwitch = false;
break caseStmts;
}
}
canUseIfElseSwitch &= hasSingletonNullCase;
if (canUseIfElseSwitch) {
// yes, so use a If
transformation = new IfNullElseSwitch();
}
}
}
// The default transformation
if (transformation == null) {
transformation = new IfElseChain();
}
JCStatement result = transformation.transformSwitch(node, switchClause, caseList, tmpVar, outerExpression, expectedType);
unblock();
return result;
}
use of com.redhat.ceylon.compiler.typechecker.tree.Tree.Expression in project ceylon-compiler by ceylon.
the class StatementTransformer method getDocAnnotationText.
private String getDocAnnotationText(Tree.Assertion ass) {
String docText = null;
Tree.Annotation doc = getAnnotation(ass.getAnnotationList(), "doc");
if (doc != null) {
Tree.Expression expression = null;
if (doc.getPositionalArgumentList() != null) {
Tree.PositionalArgument arg = doc.getPositionalArgumentList().getPositionalArguments().get(0);
if (arg instanceof Tree.ListedArgument)
expression = ((Tree.ListedArgument) arg).getExpression();
else
throw new BugException(arg, "argument to doc annotation cannot be a spread argument or comprehension: " + arg);
} else if (doc.getNamedArgumentList() != null) {
Tree.SpecifiedArgument arg = (Tree.SpecifiedArgument) doc.getNamedArgumentList().getNamedArguments().get(0);
expression = arg.getSpecifierExpression().getExpression();
} else {
// Impossible on a well-formed tree
return null;
}
Tree.Literal literal = (Tree.Literal) expression.getTerm();
docText = literal.getText();
} else if (ass.getAnnotationList() != null && ass.getAnnotationList().getAnonymousAnnotation() != null) {
docText = ass.getAnnotationList().getAnonymousAnnotation().getStringLiteral().getText();
}
return docText;
}
Aggregations