Search in sources :

Example 66 with JCExpression

use of org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression in project ceylon by eclipse.

the class ExpressionTransformer method makeOptimizedInIntegerOrCharacterMeasure.

protected JCTree makeOptimizedInIntegerOrCharacterMeasure(Tree.InOp op, org.eclipse.ceylon.langtools.tools.javac.code.Type ceylonType, org.eclipse.ceylon.langtools.tools.javac.code.Type javaType) {
    Tree.SegmentOp rangeOp = (Tree.SegmentOp) op.getRightTerm();
    SyntheticName xName = naming.temp("x");
    SyntheticName yName = naming.temp("y");
    SyntheticName zName = naming.temp("z");
    SyntheticName wName = naming.temp("w");
    JCExpression x = transformExpression(op.getLeftTerm(), BoxingStrategy.UNBOXED, typeFact().getObjectType());
    JCExpression y = transformExpression(rangeOp.getLeftTerm(), BoxingStrategy.UNBOXED, rangeOp.getLeftTerm().getTypeModel());
    JCExpression z = transformExpression(rangeOp.getRightTerm(), BoxingStrategy.UNBOXED, rangeOp.getRightTerm().getTypeModel());
    JCExpression w = make().Apply(null, naming.makeSelect(make().QualIdent(ceylonType.tsym), "offset"), List.<JCExpression>of(xName.makeIdent(), yName.makeIdent()));
    return make().LetExpr(List.<JCStatement>of(makeVar(xName, make().Type(javaType), x), makeVar(yName, make().Type(javaType), y), makeVar(zName, make().Type(syms().longType), z), makeVar(wName, make().Type(syms().longType), w)), make().Binary(JCTree.Tag.AND, make().Binary(JCTree.Tag.GT, zName.makeIdent(), make().Literal(0L)), make().Binary(JCTree.Tag.AND, make().Binary(JCTree.Tag.LE, make().Literal(0L), wName.makeIdent()), make().Binary(JCTree.Tag.LT, wName.makeIdent(), zName.makeIdent()))));
}
Also used : JCExpression(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression) JCTree(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree) Tree(org.eclipse.ceylon.compiler.typechecker.tree.Tree) SyntheticName(org.eclipse.ceylon.compiler.java.codegen.Naming.SyntheticName)

Example 67 with JCExpression

use of org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression in project ceylon by eclipse.

the class ExpressionTransformer method checkForBitwiseOperators.

private JCExpression checkForBitwiseOperators(Tree.Term node, Tree.QualifiedMemberExpression qme, Tree.Term right) {
    // must be a call on Integer
    Tree.Term left = qme.getPrimary();
    if (left == null) {
        return null;
    }
    String signature;
    Type binaryType;
    if (isCeylonInteger(left.getTypeModel())) {
        // must be a supported method/attribute
        binaryType = typeFact().getIntegerType();
        String name = qme.getIdentifier().getText();
        signature = "ceylon.language.Integer." + name;
    } else if (isCeylonByte(left.getTypeModel())) {
        binaryType = typeFact().getByteType();
        String name = qme.getIdentifier().getText();
        signature = "ceylon.language.Byte." + name;
    } else {
        return null;
    }
    // see if we have an operator for it
    OperatorTranslation operator = Operators.getOperator(signature);
    if (operator != null) {
        JCExpression result;
        if (operator.getArity() == 2) {
            if (right == null)
                return null;
            OptimisationStrategy optimisationStrategy = operator.getBinOpOptimisationStrategy(node, left, right, this);
            // check that we can optimise it
            if (!optimisationStrategy.useJavaOperator())
                return null;
            JCExpression leftExpr = transformExpression(left, optimisationStrategy.getBoxingStrategy(), binaryType, EXPR_WIDEN_PRIM);
            JCExpression rightExpr = transformExpression(right, optimisationStrategy.getBoxingStrategy(), binaryType, EXPR_WIDEN_PRIM);
            if (operator.leftValueMask != 0) {
                leftExpr = make().Binary(JCTree.Tag.BITAND, leftExpr, makeInteger(operator.leftValueMask));
            }
            if (operator.rightValueMask != 0) {
                rightExpr = make().Binary(JCTree.Tag.BITAND, rightExpr, makeInteger(operator.rightValueMask));
            }
            result = make().Binary(operator.javacOperator, leftExpr, rightExpr);
        } else {
            // must be unary
            if (right != null)
                return null;
            OptimisationStrategy optimisationStrategy = operator.getUnOpOptimisationStrategy(node, left, this);
            // check that we can optimise it
            if (!optimisationStrategy.useJavaOperator())
                return null;
            JCExpression leftExpr = transformExpression(left, optimisationStrategy.getBoxingStrategy(), binaryType, EXPR_WIDEN_PRIM);
            if (operator.leftValueMask != 0) {
                leftExpr = make().Binary(JCTree.Tag.BITAND, leftExpr, makeInteger(operator.leftValueMask));
            }
            result = make().Unary(operator.javacOperator, leftExpr);
        }
        if (isCeylonByte(binaryType)) {
            result = make().TypeCast(syms().byteType, result);
        }
        return result;
    }
    return null;
}
Also used : UnionType(org.eclipse.ceylon.model.typechecker.model.UnionType) Type(org.eclipse.ceylon.model.typechecker.model.Type) JCExpression(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression) Term(org.eclipse.ceylon.compiler.typechecker.tree.Tree.Term) JCTree(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree) Tree(org.eclipse.ceylon.compiler.typechecker.tree.Tree) OptimisationStrategy(org.eclipse.ceylon.compiler.java.codegen.Operators.OptimisationStrategy) OperatorTranslation(org.eclipse.ceylon.compiler.java.codegen.Operators.OperatorTranslation) AssignmentOperatorTranslation(org.eclipse.ceylon.compiler.java.codegen.Operators.AssignmentOperatorTranslation)

Example 68 with JCExpression

use of org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression in project ceylon by eclipse.

the class ExpressionTransformer method transform.

public JCTree transform(Tree.TypeLiteral expr) {
    at(expr);
    if (!expr.getWantsDeclaration()) {
        if (expr.getDeclaration() instanceof Constructor) {
            JCExpression classLiteral = makeTypeLiteralCall(expr.getType().getTypeModel().getQualifyingType(), false, expr.getTypeModel());
            TypeDeclaration classModelDeclaration = (TypeDeclaration) typeFact().getLanguageModuleModelDeclaration(expr.getType().getTypeModel().getQualifyingType().getDeclaration().isMember() ? "MemberClass" : "Class");
            JCTypeCast typeCast = make().TypeCast(makeJavaType(classModelDeclaration.appliedType(null, List.of(expr.getType().getTypeModel().getQualifyingType(), typeFact().getNothingType()))), classLiteral);
            Type callableType = expr.getTypeModel().getFullType();
            JCExpression reifiedArgumentsExpr = makeReifiedTypeArgument(typeFact().getCallableTuple(callableType));
            return make().Apply(null, naming.makeQualIdent(typeCast, "getConstructor"), List.<JCExpression>of(reifiedArgumentsExpr, make().Literal(expr.getDeclaration().getName())));
        } else {
            if (coerced) {
                Type t = expr.getType().getTypeModel();
                if (!typeFact().isJavaObjectArrayType(t) || t.getTypeArgumentList().get(0).isClassOrInterface()) {
                    return makeSelect(makeJavaType(t, JT_NO_PRIMITIVES | JT_RAW), "class");
                }
            }
            return makeTypeLiteralCall(expr.getType().getTypeModel(), true, expr.getTypeModel());
        }
    } else if (expr.getDeclaration() instanceof TypeParameter) {
        // we must get it from its container
        TypeParameter declaration = (TypeParameter) expr.getDeclaration();
        Node node = expr;
        return makeTypeParameterDeclaration(node, declaration);
    } else if (expr.getDeclaration() instanceof Constructor || expr instanceof Tree.NewLiteral) {
        Constructor ctor;
        if (expr.getDeclaration() instanceof Constructor) {
            ctor = (Constructor) expr.getDeclaration();
        } else {
            ctor = ((Class) expr.getDeclaration()).getDefaultConstructor();
        }
        JCExpression metamodelCall = makeTypeDeclarationLiteral(ModelUtil.getConstructedClass(ctor));
        metamodelCall = make().TypeCast(makeJavaType(typeFact().getClassDeclarationType(), JT_RAW), metamodelCall);
        metamodelCall = make().Apply(null, naming.makeQualIdent(metamodelCall, "getConstructorDeclaration"), List.<JCExpression>of(make().Literal(ctor.getName() == null ? "" : ctor.getName())));
        if (ModelUtil.isEnumeratedConstructor(ctor)) {
            metamodelCall = make().TypeCast(makeJavaType(typeFact().getValueConstructorDeclarationType(), JT_RAW), metamodelCall);
        } else /*else if (Decl.isDefaultConstructor(ctor)){
                metamodelCall = make().TypeCast(
                        makeJavaType(typeFact().getDefaultConstructorDeclarationType(), JT_RAW), metamodelCall);
            } */
        {
            metamodelCall = make().TypeCast(makeJavaType(typeFact().getCallableConstructorDeclarationType(), JT_RAW), metamodelCall);
        }
        return metamodelCall;
    } else if (expr.getDeclaration() instanceof ClassOrInterface || expr.getDeclaration() instanceof TypeAlias) {
        // use the generated class to get to the declaration literal
        JCExpression metamodelCall = makeTypeDeclarationLiteral((TypeDeclaration) expr.getDeclaration());
        Type exprType = expr.getTypeModel().resolveAliases();
        // now cast if required
        if (!exprType.isExactly(((TypeDeclaration) typeFact().getLanguageModuleDeclarationDeclaration("NestableDeclaration")).getType())) {
            JCExpression type = makeJavaType(exprType, JT_NO_PRIMITIVES);
            return make().TypeCast(type, metamodelCall);
        }
        return metamodelCall;
    } else {
        return makeErroneous(expr, "compiler bug: " + expr.getDeclaration() + " is an unsupported declaration type");
    }
}
Also used : ClassOrInterface(org.eclipse.ceylon.model.typechecker.model.ClassOrInterface) UnionType(org.eclipse.ceylon.model.typechecker.model.UnionType) Type(org.eclipse.ceylon.model.typechecker.model.Type) TypeParameter(org.eclipse.ceylon.model.typechecker.model.TypeParameter) JCExpression(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression) JCTypeCast(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCTypeCast) Constructor(org.eclipse.ceylon.model.typechecker.model.Constructor) Node(org.eclipse.ceylon.compiler.typechecker.tree.Node) JCTree(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree) Tree(org.eclipse.ceylon.compiler.typechecker.tree.Tree) TypeAlias(org.eclipse.ceylon.model.typechecker.model.TypeAlias) TypeDeclaration(org.eclipse.ceylon.model.typechecker.model.TypeDeclaration)

Example 69 with JCExpression

use of org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression in project ceylon by eclipse.

the class ExpressionTransformer method transformUnknownArguments.

private ExpressionAndType transformUnknownArguments(SimpleInvocation invocation, CallBuilder callBuilder) {
    // doesn't really matter, assume Object, it's not used
    Type iteratedType = typeFact().getObjectType();
    // the single spread argument which is allowed
    JCExpression rest = null;
    ListBuffer<JCExpression> initial = new ListBuffer<JCExpression>();
    for (int ii = 0; ii < invocation.getNumArguments(); ii++) {
        if (invocation.isArgumentSpread(ii)) {
            rest = invocation.getTransformedArgumentExpression(ii);
        } else {
            initial.add(invocation.getTransformedArgumentExpression(ii));
        }
    }
    JCExpression expr;
    if (initial.isEmpty()) {
        expr = make().TypeCast(makeJavaType(typeFact().getSequentialDeclaration().getType(), JT_RAW), rest);
    } else {
        expr = utilInvocation().sequentialInstance(null, makeReifiedTypeArgument(iteratedType), rest != null ? rest : makeEmptyAsSequential(true), initial.toList());
    }
    JCExpression type = makeJavaType(typeFact().getSequenceType(iteratedType).getType());
    return new ExpressionAndType(expr, type);
}
Also used : UnionType(org.eclipse.ceylon.model.typechecker.model.UnionType) Type(org.eclipse.ceylon.model.typechecker.model.Type) JCExpression(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression) ListBuffer(org.eclipse.ceylon.langtools.tools.javac.util.ListBuffer)

Example 70 with JCExpression

use of org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression in project ceylon by eclipse.

the class ExpressionTransformer method transform.

public JCExpression transform(Tree.DefaultOp op) {
    Term elseTerm = unwrapExpressionUntilTerm(op.getRightTerm());
    Type typeModel = typeFact().denotableType(op.getTypeModel());
    // make sure we do not insert null checks if we're going to allow testing for null
    Type rightExpectedType = getOptionalTypeForInteropIfAllowed(expectedType, typeModel, elseTerm);
    if (unwrapExpressionUntilTerm(op.getLeftTerm()) instanceof Tree.ThenOp) {
        // Optimize cond then foo else bar (avoids unnecessary boxing in particular)
        Tree.ThenOp then = (Tree.ThenOp) unwrapExpressionUntilTerm(op.getLeftTerm());
        Term condTerm = then.getLeftTerm();
        Term thenTerm = then.getRightTerm();
        JCExpression cond = transformExpression(condTerm, BoxingStrategy.UNBOXED, condTerm.getTypeModel());
        JCExpression thenpart = transformExpression(thenTerm, CodegenUtil.getBoxingStrategy(op), rightExpectedType);
        JCExpression elsepart = transformExpression(elseTerm, CodegenUtil.getBoxingStrategy(op), rightExpectedType);
        return make().Conditional(cond, thenpart, elsepart);
    }
    JCExpression left = transformExpression(op.getLeftTerm(), BoxingStrategy.BOXED, typeFact().getOptionalType(typeModel));
    JCExpression right = transformExpression(elseTerm, BoxingStrategy.BOXED, rightExpectedType);
    Naming.SyntheticName varName = naming.temp();
    JCExpression varIdent = varName.makeIdent();
    JCExpression test = at(op).Binary(JCTree.Tag.NE, varIdent, makeNull());
    JCExpression cond = make().Conditional(test, varIdent, right);
    JCExpression typeExpr = makeJavaType(typeModel, JT_NO_PRIMITIVES);
    return makeLetExpr(varName, null, typeExpr, left, cond);
}
Also used : UnionType(org.eclipse.ceylon.model.typechecker.model.UnionType) Type(org.eclipse.ceylon.model.typechecker.model.Type) JCExpression(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression) JCTree(org.eclipse.ceylon.langtools.tools.javac.tree.JCTree) Tree(org.eclipse.ceylon.compiler.typechecker.tree.Tree) SyntheticName(org.eclipse.ceylon.compiler.java.codegen.Naming.SyntheticName) Term(org.eclipse.ceylon.compiler.typechecker.tree.Tree.Term) TreeUtil.unwrapExpressionUntilTerm(org.eclipse.ceylon.compiler.typechecker.tree.TreeUtil.unwrapExpressionUntilTerm)

Aggregations

JCExpression (org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCExpression)224 JCTree (org.eclipse.ceylon.langtools.tools.javac.tree.JCTree)95 Type (org.eclipse.ceylon.model.typechecker.model.Type)95 Tree (org.eclipse.ceylon.compiler.typechecker.tree.Tree)74 JCStatement (org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCStatement)53 ListBuffer (org.eclipse.ceylon.langtools.tools.javac.util.ListBuffer)53 UnionType (org.eclipse.ceylon.model.typechecker.model.UnionType)45 SyntheticName (org.eclipse.ceylon.compiler.java.codegen.Naming.SyntheticName)41 TypeDeclaration (org.eclipse.ceylon.model.typechecker.model.TypeDeclaration)39 TypedDeclaration (org.eclipse.ceylon.model.typechecker.model.TypedDeclaration)38 Declaration (org.eclipse.ceylon.model.typechecker.model.Declaration)33 TypeParameter (org.eclipse.ceylon.model.typechecker.model.TypeParameter)32 Parameter (org.eclipse.ceylon.model.typechecker.model.Parameter)30 JCVariableDecl (org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCVariableDecl)28 Function (org.eclipse.ceylon.model.typechecker.model.Function)26 ClassOrInterface (org.eclipse.ceylon.model.typechecker.model.ClassOrInterface)22 Value (org.eclipse.ceylon.model.typechecker.model.Value)22 JCNewClass (org.eclipse.ceylon.langtools.tools.javac.tree.JCTree.JCNewClass)21 FunctionOrValue (org.eclipse.ceylon.model.typechecker.model.FunctionOrValue)21 Class (org.eclipse.ceylon.model.typechecker.model.Class)17