Search in sources :

Example 1 with SpecifierExpression

use of com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression in project ceylon-compiler by ceylon.

the class ClassTransformer method transformRefinementSpecifierStatement.

public List<JCStatement> transformRefinementSpecifierStatement(SpecifierStatement op, ClassDefinitionBuilder classBuilder) {
    List<JCStatement> result = List.<JCStatement>nil();
    // Check if this is a shortcut form of formal attribute refinement
    if (op.getRefinement()) {
        Tree.Term baseMemberTerm = op.getBaseMemberExpression();
        if (baseMemberTerm instanceof Tree.ParameterizedExpression)
            baseMemberTerm = ((Tree.ParameterizedExpression) baseMemberTerm).getPrimary();
        Tree.BaseMemberExpression expr = (BaseMemberExpression) baseMemberTerm;
        Declaration decl = expr.getDeclaration();
        if (Decl.isValue(decl) || Decl.isGetter(decl)) {
            // Now build a "fake" declaration for the attribute
            Tree.AttributeDeclaration attrDecl = new Tree.AttributeDeclaration(null);
            attrDecl.setDeclarationModel((Value) decl);
            attrDecl.setIdentifier(expr.getIdentifier());
            attrDecl.setScope(op.getScope());
            attrDecl.setSpecifierOrInitializerExpression(op.getSpecifierExpression());
            attrDecl.setAnnotationList(makeShortcutRefinementAnnotationTrees());
            // Make sure the boxing information is set correctly
            BoxingDeclarationVisitor v = new CompilerBoxingDeclarationVisitor(this);
            v.visit(attrDecl);
            // Generate the attribute
            transform(attrDecl, classBuilder);
        } else if (decl instanceof Function) {
            // Now build a "fake" declaration for the method
            Tree.MethodDeclaration methDecl = new Tree.MethodDeclaration(null);
            Function m = (Function) decl;
            methDecl.setDeclarationModel(m);
            methDecl.setIdentifier(expr.getIdentifier());
            methDecl.setScope(op.getScope());
            methDecl.setAnnotationList(makeShortcutRefinementAnnotationTrees());
            Tree.SpecifierExpression specifierExpression = op.getSpecifierExpression();
            methDecl.setSpecifierExpression(specifierExpression);
            if (specifierExpression instanceof Tree.LazySpecifierExpression == false) {
                Tree.Expression expression = specifierExpression.getExpression();
                Tree.Term expressionTerm = Decl.unwrapExpressionsUntilTerm(expression);
                // we can optimise lambdas and static method calls
                if (!CodegenUtil.canOptimiseMethodSpecifier(expressionTerm, m)) {
                    // we need a field to save the callable value
                    String name = naming.getMethodSpecifierAttributeName(m);
                    JCExpression specifierType = makeJavaType(expression.getTypeModel());
                    JCExpression specifier = expressionGen().transformExpression(expression);
                    classBuilder.field(PRIVATE | FINAL, name, specifierType, specifier, false);
                }
            }
            java.util.List<Tree.ParameterList> parameterListTrees = null;
            if (op.getBaseMemberExpression() instanceof Tree.ParameterizedExpression) {
                parameterListTrees = new ArrayList<>(m.getParameterLists().size());
                parameterListTrees.addAll(((Tree.ParameterizedExpression) op.getBaseMemberExpression()).getParameterLists());
                Tree.Term term = specifierExpression.getExpression().getTerm();
                // and give it the given block of expr as it's specifier
                while (term instanceof Tree.FunctionArgument && m.getParameterLists().size() > 1) {
                    FunctionArgument functionArgument = (Tree.FunctionArgument) term;
                    specifierExpression.setExpression(functionArgument.getExpression());
                    parameterListTrees.addAll(functionArgument.getParameterLists());
                    term = functionArgument.getExpression().getTerm();
                }
            }
            int plIndex = 0;
            // copy from formal declaration
            for (ParameterList pl : m.getParameterLists()) {
                Tree.ParameterList parameterListTree = null;
                if (parameterListTrees != null)
                    parameterListTree = parameterListTrees.get(plIndex++);
                Tree.ParameterList tpl = new Tree.ParameterList(null);
                tpl.setModel(pl);
                int pIndex = 0;
                for (Parameter p : pl.getParameters()) {
                    Tree.Parameter parameterTree = null;
                    if (parameterListTree != null)
                        parameterTree = parameterListTree.getParameters().get(pIndex++);
                    Tree.Parameter tp = null;
                    if (p.getModel() instanceof Value) {
                        Tree.ValueParameterDeclaration tvpd = new Tree.ValueParameterDeclaration(null);
                        if (parameterTree != null)
                            tvpd.setTypedDeclaration(((Tree.ParameterDeclaration) parameterTree).getTypedDeclaration());
                        tvpd.setParameterModel(p);
                        tp = tvpd;
                    } else if (p.getModel() instanceof Function) {
                        Tree.FunctionalParameterDeclaration tfpd = new Tree.FunctionalParameterDeclaration(null);
                        if (parameterTree != null)
                            tfpd.setTypedDeclaration(((Tree.ParameterDeclaration) parameterTree).getTypedDeclaration());
                        tfpd.setParameterModel(p);
                        tp = tfpd;
                    } else {
                        throw BugException.unhandledDeclarationCase(p.getModel());
                    }
                    tp.setScope(p.getDeclaration().getContainer());
                    // tp.setIdentifier(makeIdentifier(p.getName()));
                    tpl.addParameter(tp);
                }
                methDecl.addParameterList(tpl);
            }
            // Make sure the boxing information is set correctly
            BoxingDeclarationVisitor v = new CompilerBoxingDeclarationVisitor(this);
            v.visit(methDecl);
            // Generate the method
            classBuilder.method(methDecl, Errors.GENERATE);
        }
    } else {
        // Normal case, just generate the specifier statement
        result = result.append(expressionGen().transform(op));
    }
    Tree.Term term = op.getBaseMemberExpression();
    if (term instanceof Tree.BaseMemberExpression) {
        Tree.BaseMemberExpression bme = (Tree.BaseMemberExpression) term;
        DeferredSpecification ds = statementGen().getDeferredSpecification(bme.getDeclaration());
        if (ds != null && needsInnerSubstitution(term.getScope(), bme.getDeclaration())) {
            result = result.append(ds.openInnerSubstitution());
        }
    }
    return result;
}
Also used : AttributeDeclaration(com.redhat.ceylon.compiler.typechecker.tree.Tree.AttributeDeclaration) LazySpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.LazySpecifierExpression) SpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression) DeferredSpecification(com.redhat.ceylon.compiler.java.codegen.StatementTransformer.DeferredSpecification) ArrayList(java.util.ArrayList) JCStatement(com.sun.tools.javac.tree.JCTree.JCStatement) Function(com.redhat.ceylon.model.typechecker.model.Function) JCPrimitiveTypeTree(com.sun.tools.javac.tree.JCTree.JCPrimitiveTypeTree) JCTree(com.sun.tools.javac.tree.JCTree) Tree(com.redhat.ceylon.compiler.typechecker.tree.Tree) ArrayList(java.util.ArrayList) AnnotationList(com.redhat.ceylon.compiler.typechecker.tree.Tree.AnnotationList) List(com.sun.tools.javac.util.List) ParameterList(com.redhat.ceylon.model.typechecker.model.ParameterList) TypedDeclaration(com.redhat.ceylon.model.typechecker.model.TypedDeclaration) Declaration(com.redhat.ceylon.model.typechecker.model.Declaration) TypeDeclaration(com.redhat.ceylon.model.typechecker.model.TypeDeclaration) MethodDeclaration(com.redhat.ceylon.compiler.typechecker.tree.Tree.MethodDeclaration) AttributeDeclaration(com.redhat.ceylon.compiler.typechecker.tree.Tree.AttributeDeclaration) FunctionArgument(com.redhat.ceylon.compiler.typechecker.tree.Tree.FunctionArgument) LazySpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.LazySpecifierExpression) BaseMemberExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.BaseMemberExpression) MethodDeclaration(com.redhat.ceylon.compiler.typechecker.tree.Tree.MethodDeclaration) MethodDeclaration(com.redhat.ceylon.compiler.typechecker.tree.Tree.MethodDeclaration) AttributeDeclaration(com.redhat.ceylon.compiler.typechecker.tree.Tree.AttributeDeclaration) JCExpression(com.sun.tools.javac.tree.JCTree.JCExpression) LazySpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.LazySpecifierExpression) SpecifierOrInitializerExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierOrInitializerExpression) JCExpression(com.sun.tools.javac.tree.JCTree.JCExpression) SpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression) BaseMemberExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.BaseMemberExpression) FunctionOrValue(com.redhat.ceylon.model.typechecker.model.FunctionOrValue) JavaBeanValue(com.redhat.ceylon.model.loader.model.JavaBeanValue) Value(com.redhat.ceylon.model.typechecker.model.Value) ParameterList(com.redhat.ceylon.model.typechecker.model.ParameterList) TypeParameter(com.redhat.ceylon.model.typechecker.model.TypeParameter) Parameter(com.redhat.ceylon.model.typechecker.model.Parameter) BaseMemberExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.BaseMemberExpression)

Example 2 with SpecifierExpression

use of com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression in project ceylon-compiler by ceylon.

the class ClassTransformer method transform.

List<MethodDefinitionBuilder> transform(Tree.AnyMethod def, ClassDefinitionBuilder classBuilder, List<JCStatement> body) {
    final Function model = def.getDeclarationModel();
    List<MethodDefinitionBuilder> result = List.<MethodDefinitionBuilder>nil();
    if (!Decl.withinInterface(model)) {
        // Transform to the class
        boolean refinedResultType = !model.getType().isExactly(((TypedDeclaration) model.getRefinedDeclaration()).getType());
        result = transformMethod(def, true, true, true, transformMplBodyUnlessSpecifier(def, model, body), refinedResultType && !Decl.withinInterface(model.getRefinedDeclaration()) ? new DaoSuper() : new DaoThis(def, def.getParameterLists().get(0)), !Strategy.defaultParameterMethodOnSelf(model));
    } else {
        // Is within interface
        // Transform the definition to the companion class, how depends
        // on what kind of method it is
        List<MethodDefinitionBuilder> companionDefs;
        if (def instanceof Tree.MethodDeclaration) {
            final SpecifierExpression specifier = ((Tree.MethodDeclaration) def).getSpecifierExpression();
            if (specifier == null) {
                // formal or abstract
                // (still need overloads and DPMs on the companion)
                companionDefs = transformMethod(def, false, true, true, null, new DaoCompanion(def, def.getParameterLists().get(0)), false);
            } else {
                companionDefs = transformMethod(def, true, false, !model.isShared(), transformMplBodyUnlessSpecifier(def, model, body), new DaoCompanion(def, def.getParameterLists().get(0)), false);
            }
        } else if (def instanceof Tree.MethodDefinition) {
            companionDefs = transformMethod(def, true, false, !model.isShared(), transformMplBodyUnlessSpecifier(def, model, body), new DaoCompanion(def, def.getParameterLists().get(0)), false);
        } else {
            throw BugException.unhandledNodeCase(def);
        }
        if (!companionDefs.isEmpty())
            classBuilder.getCompanionBuilder((TypeDeclaration) model.getContainer()).methods(companionDefs);
        // but only if it's shared
        if (Decl.isShared(model)) {
            result = transformMethod(def, true, true, true, null, daoAbstract, !Strategy.defaultParameterMethodOnSelf(model));
        }
    }
    return result;
}
Also used : Function(com.redhat.ceylon.model.typechecker.model.Function) TypedDeclaration(com.redhat.ceylon.model.typechecker.model.TypedDeclaration) LazySpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.LazySpecifierExpression) SpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression) MethodDeclaration(com.redhat.ceylon.compiler.typechecker.tree.Tree.MethodDeclaration) JCPrimitiveTypeTree(com.sun.tools.javac.tree.JCTree.JCPrimitiveTypeTree) JCTree(com.sun.tools.javac.tree.JCTree) Tree(com.redhat.ceylon.compiler.typechecker.tree.Tree)

Example 3 with SpecifierExpression

use of com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression in project ceylon-compiler by ceylon.

the class MethodOrValueReferenceVisitor method visit.

@Override
public void visit(Tree.MethodDeclaration that) {
    super.visit(that);
    final SpecifierExpression specifier = that.getSpecifierExpression();
    if (specifier != null && specifier instanceof Tree.LazySpecifierExpression) {
        boolean cs = enterCapturingScope();
        specifier.visit(this);
        exitCapturingScope(cs);
    }
}
Also used : LazySpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.LazySpecifierExpression) LazySpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.LazySpecifierExpression) SpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression) Tree(com.redhat.ceylon.compiler.typechecker.tree.Tree)

Example 4 with SpecifierExpression

use of com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression 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);
}
Also used : LazySpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.LazySpecifierExpression) SpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression) LazySpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.LazySpecifierExpression) Expression(com.redhat.ceylon.compiler.typechecker.tree.Tree.Expression) SpecifierExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression) SpecifierOrInitializerExpression(com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierOrInitializerExpression) Primary(com.redhat.ceylon.compiler.typechecker.tree.Tree.Primary) Tree(com.redhat.ceylon.compiler.typechecker.tree.Tree) Term(com.redhat.ceylon.compiler.typechecker.tree.Tree.Term)

Aggregations

Tree (com.redhat.ceylon.compiler.typechecker.tree.Tree)4 LazySpecifierExpression (com.redhat.ceylon.compiler.typechecker.tree.Tree.LazySpecifierExpression)4 SpecifierExpression (com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierExpression)4 MethodDeclaration (com.redhat.ceylon.compiler.typechecker.tree.Tree.MethodDeclaration)2 SpecifierOrInitializerExpression (com.redhat.ceylon.compiler.typechecker.tree.Tree.SpecifierOrInitializerExpression)2 Function (com.redhat.ceylon.model.typechecker.model.Function)2 TypedDeclaration (com.redhat.ceylon.model.typechecker.model.TypedDeclaration)2 JCTree (com.sun.tools.javac.tree.JCTree)2 JCPrimitiveTypeTree (com.sun.tools.javac.tree.JCTree.JCPrimitiveTypeTree)2 DeferredSpecification (com.redhat.ceylon.compiler.java.codegen.StatementTransformer.DeferredSpecification)1 AnnotationList (com.redhat.ceylon.compiler.typechecker.tree.Tree.AnnotationList)1 AttributeDeclaration (com.redhat.ceylon.compiler.typechecker.tree.Tree.AttributeDeclaration)1 BaseMemberExpression (com.redhat.ceylon.compiler.typechecker.tree.Tree.BaseMemberExpression)1 Expression (com.redhat.ceylon.compiler.typechecker.tree.Tree.Expression)1 FunctionArgument (com.redhat.ceylon.compiler.typechecker.tree.Tree.FunctionArgument)1 Primary (com.redhat.ceylon.compiler.typechecker.tree.Tree.Primary)1 Term (com.redhat.ceylon.compiler.typechecker.tree.Tree.Term)1 JavaBeanValue (com.redhat.ceylon.model.loader.model.JavaBeanValue)1 Declaration (com.redhat.ceylon.model.typechecker.model.Declaration)1 FunctionOrValue (com.redhat.ceylon.model.typechecker.model.FunctionOrValue)1