Search in sources :

Example 1 with MathExpr

use of kalang.ast.MathExpr in project kalang by kasonyang.

the class Ast2Class method visitIncrementExpr.

@Override
public Object visitIncrementExpr(IncrementExpr node) {
    if (!node.isIsPrefix()) {
        visit(node.getExpr());
    }
    Type exprType = node.getExpr().getType();
    ConstExpr ce = getConstX(exprType, node.isIsDesc() ? -1 : 1);
    BinaryExpr be = new MathExpr(node.getExpr(), ce, "+");
    AssignExpr addOne = new AssignExpr(node.getExpr(), be);
    visit(addOne);
    pop(exprType);
    if (node.isIsPrefix()) {
        visit(node.getExpr());
    }
    return null;
}
Also used : Type(kalang.core.Type) GenericType(kalang.core.GenericType) WildcardType(kalang.core.WildcardType) ArrayType(kalang.core.ArrayType) ObjectType(kalang.core.ObjectType) ClassType(kalang.core.ClassType) PrimitiveType(kalang.core.PrimitiveType) ConstExpr(kalang.ast.ConstExpr) BinaryExpr(kalang.ast.BinaryExpr) MathExpr(kalang.ast.MathExpr) AssignExpr(kalang.ast.AssignExpr)

Example 2 with MathExpr

use of kalang.ast.MathExpr in project kalang by kasonyang.

the class AstBuilder method visitInvokeExpr.

@Override
public AstNode visitInvokeExpr(InvokeExprContext ctx) {
    Object target = visit(ctx.target);
    if (target == null)
        return null;
    String mdName = ctx.Identifier().getText();
    String refKey = ctx.refKey.getText();
    if (refKey.equals(".")) {
        if (target instanceof ClassReference) {
            return getStaticInvokeExpr((ClassReference) target, mdName, ctx.params, ctx);
        } else if (target instanceof ExprNode) {
            return getObjectInvokeExpr((ExprNode) target, mdName, ctx.params, ctx);
        } else {
            throw Exceptions.unexceptedValue(target);
        }
    } else if (refKey.equals("->")) {
        ExprNode[] invokeArgs = new ExprNode[3];
        ExprNode[] params = new ExprNode[ctx.params.size()];
        if (target instanceof ClassReference) {
            invokeArgs[0] = new ConstExpr(null);
        } else if (target instanceof ExprNode) {
            invokeArgs[0] = ((ExprNode) target);
        }
        invokeArgs[1] = new ConstExpr(mdName);
        for (int i = 0; i < params.length; i++) {
            params[i] = visitExpression(ctx.params.get(i));
        }
        invokeArgs[2] = createInitializedArray(Types.getRootType(), params);
        ClassNode dispatcherAst = getAst("kalang.runtime.dynamic.MethodDispatcher");
        if (dispatcherAst == null) {
            throw Exceptions.unexceptedException("Runtime library is required!");
        }
        return getStaticInvokeExpr(new ClassReference(dispatcherAst), "invokeMethod", invokeArgs, ctx);
    } else if (refKey.equals("*.")) {
        if (!(target instanceof ExprNode)) {
            handleSyntaxError("expression required", ctx.expression);
            return null;
        }
        ExprNode targetExpr = (ExprNode) target;
        Type targetType = targetExpr.getType();
        if (!(targetType instanceof ArrayType)) {
            handleSyntaxError("array required", ctx.expression);
            return null;
        }
        List<Statement> stats = new LinkedList();
        LocalVarNode varArrLen = this.declareTempLocalVar(Types.INT_TYPE);
        LocalVarNode varCounter = this.declareTempLocalVar(Types.INT_TYPE);
        stats.add(new VarDeclStmt(Arrays.asList(varArrLen, varCounter)));
        VarExpr varArrLenExpr = new VarExpr(varArrLen);
        VarExpr varCounterExpr = new VarExpr(varCounter);
        stats.add(new ExprStmt(new AssignExpr(varArrLenExpr, new ArrayLengthExpr(targetExpr))));
        stats.add(new ExprStmt(new AssignExpr(varCounterExpr, new ConstExpr(0))));
        CompareExpr conditionExpr = new CompareExpr(varCounterExpr, varArrLenExpr, CompareExpr.OP_LT);
        ExprNode targetEleExpr = new ElementExpr(targetExpr, varCounterExpr);
        ExprNode invokeExpr = getObjectInvokeExpr(targetEleExpr, mdName, ctx.params, ctx);
        if (invokeExpr == null)
            return null;
        LocalVarNode varRet = this.declareTempLocalVar(Types.getArrayType(invokeExpr.getType()));
        VarExpr varRetExpr = new VarExpr(varRet);
        stats.add(new VarDeclStmt(varRet));
        stats.add(new ExprStmt(new AssignExpr(varRetExpr, new NewArrayExpr(invokeExpr.getType(), varArrLenExpr))));
        BlockStmt loopBody = this.newBlock();
        loopBody.statements.add(new ExprStmt(new AssignExpr(new ElementExpr(varRetExpr, varCounterExpr), invokeExpr)));
        popBlock();
        BlockStmt updateBs = newBlock();
        updateBs.statements.add(new ExprStmt(new AssignExpr(varCounterExpr, new MathExpr(varCounterExpr, new ConstExpr(1), MathExpr.OP_ADD))));
        this.popBlock();
        LoopStmt loopStmt = new LoopStmt(conditionExpr, null, loopBody, updateBs);
        stats.add(loopStmt);
        return new MultiStmtExpr(stats, varRetExpr);
    } else {
        throw Exceptions.unexceptedException(refKey);
    }
}
Also used : ClassNode(kalang.ast.ClassNode) ConstExpr(kalang.ast.ConstExpr) LoopStmt(kalang.ast.LoopStmt) Statement(kalang.ast.Statement) BlockStmt(kalang.ast.BlockStmt) ArrayLengthExpr(kalang.ast.ArrayLengthExpr) LinkedList(java.util.LinkedList) AssignExpr(kalang.ast.AssignExpr) ExprNode(kalang.ast.ExprNode) ArrayType(kalang.core.ArrayType) MultiStmtExpr(kalang.ast.MultiStmtExpr) WildcardType(kalang.core.WildcardType) ArrayType(kalang.core.ArrayType) ClassType(kalang.core.ClassType) PrimitiveType(kalang.core.PrimitiveType) Type(kalang.core.Type) GenericType(kalang.core.GenericType) ObjectType(kalang.core.ObjectType) ExprStmt(kalang.ast.ExprStmt) CompareExpr(kalang.ast.CompareExpr) NewArrayExpr(kalang.ast.NewArrayExpr) VarDeclStmt(kalang.ast.VarDeclStmt) VarExpr(kalang.ast.VarExpr) VarObject(kalang.ast.VarObject) ClassReference(kalang.ast.ClassReference) LocalVarNode(kalang.ast.LocalVarNode) MathExpr(kalang.ast.MathExpr) ElementExpr(kalang.ast.ElementExpr)

Example 3 with MathExpr

use of kalang.ast.MathExpr in project kalang by kasonyang.

the class AstBuilder method visitForEachStat.

@Override
public Object visitForEachStat(KalangParser.ForEachStatContext ctx) {
    BlockStmt block = newBlock();
    ExprNode expr = this.visitExpression(ctx.expression());
    Type exprType = expr.getType();
    List<TerminalNode> idsCtx = ctx.Identifier();
    VarExpr indexVarExpr = null;
    TerminalNode varId;
    if (idsCtx.size() == 1) {
        varId = idsCtx.get(0);
    } else {
        TerminalNode indexId = idsCtx.get(0);
        LocalVarNode indexVar = this.declareLocalVar(indexId.getText(), Types.INT_TYPE, Modifier.FINAL, ctx);
        if (indexVar == null)
            return null;
        block.statements.add(new VarDeclStmt(indexVar));
        indexVarExpr = new VarExpr(indexVar);
        varId = idsCtx.get(1);
    }
    LoopStmt loopStmt;
    if (exprType instanceof ArrayType) {
        LocalVarNode localVarNode = this.declareLocalVar(varId.getText(), ((ArrayType) exprType).getComponentType(), Modifier.FINAL, ctx);
        if (localVarNode == null)
            return null;
        VarExpr localVariable = new VarExpr(localVarNode);
        block.statements.add(new VarDeclStmt(localVarNode));
        LocalVarNode lenVar = this.declareTempLocalVar(Types.INT_TYPE);
        LocalVarNode counterVar = this.declareTempLocalVar(Types.INT_TYPE);
        // var len
        block.statements.add(new VarDeclStmt(lenVar));
        // var i
        block.statements.add(new VarDeclStmt(counterVar));
        VarExpr counterVarExpr = new VarExpr(counterVar);
        VarExpr lenVarExpr = new VarExpr(lenVar);
        block.statements.add(new ExprStmt(new AssignExpr(lenVarExpr, new ArrayLengthExpr(expr))));
        // l = array.length
        block.statements.add(new ExprStmt(new AssignExpr(counterVarExpr, new ConstExpr(0))));
        // i=0
        ExprNode cnd = new CompareExpr(counterVarExpr, lenVarExpr, CompareExpr.OP_LT);
        BlockStmt loopBody = this.newBlock();
        loopBody.statements.add(new ExprStmt(new AssignExpr(localVariable, new ElementExpr(expr, counterVarExpr))));
        if (indexVarExpr != null) {
            loopBody.statements.add(new ExprStmt(new AssignExpr(indexVarExpr, counterVarExpr)));
        }
        loopBody.statements.add(visitStat(ctx.stat()));
        popBlock();
        BlockStmt updateBs = newBlock();
        // increment counter
        updateBs.statements.add(new ExprStmt(new AssignExpr(counterVarExpr, new MathExpr(counterVarExpr, new ConstExpr(1), MathExpr.OP_ADD))));
        popBlock();
        loopStmt = new LoopStmt(cnd, null, loopBody, updateBs);
    } else {
        ObjectType iterType = Types.getIterableClassType();
        if (iterType.isAssignableFrom(exprType)) {
            ObjectInvokeExpr getIterableExpr;
            try {
                getIterableExpr = ObjectInvokeExpr.create(expr, "iterator", null);
            } catch (MethodNotFoundException | AmbiguousMethodException ex) {
                throw Exceptions.unexceptedException(ex);
            }
            LocalVarNode iterableVarNode = this.declareTempLocalVar(getIterableExpr.getType());
            block.statements.add(new VarDeclStmt(iterableVarNode));
            VarExpr iterableVarExpr = new VarExpr(iterableVarNode);
            block.statements.add(new ExprStmt(new AssignExpr(iterableVarExpr, getIterableExpr)));
            // set index = 0
            if (indexVarExpr != null) {
                block.statements.add(new ExprStmt(new AssignExpr(indexVarExpr, new ConstExpr(0))));
            }
            ObjectInvokeExpr cnd;
            try {
                cnd = ObjectInvokeExpr.create(iterableVarExpr, "hasNext", null);
            } catch (MethodNotFoundException | AmbiguousMethodException ex) {
                throw Exceptions.unexceptedException(ex);
            }
            BlockStmt loopBody = this.newBlock();
            ObjectInvokeExpr nextInvokeExpr;
            try {
                nextInvokeExpr = ObjectInvokeExpr.create(iterableVarExpr, "next", null);
            } catch (MethodNotFoundException | AmbiguousMethodException ex) {
                throw Exceptions.unexceptedException(ex);
            }
            LocalVarNode localVarNode = this.declareLocalVar(varId.getText(), nextInvokeExpr.getType(), Modifier.FINAL, ctx);
            if (localVarNode == null)
                return null;
            VarExpr localVariable = new VarExpr(localVarNode);
            loopBody.statements.add(new VarDeclStmt(localVarNode));
            loopBody.statements.add(new ExprStmt(new AssignExpr(localVariable, new CastExpr(localVariable.getType(), nextInvokeExpr))));
            loopBody.statements.add(visitStat(ctx.stat()));
            popBlock();
            BlockStmt updateBs = newBlock();
            if (indexVarExpr != null) {
                // do index++
                updateBs.statements.add(new ExprStmt(new AssignExpr(indexVarExpr, new MathExpr(indexVarExpr, new ConstExpr(1), BinaryExpr.OP_ADD))));
            }
            popBlock();
            loopStmt = new LoopStmt(cnd, null, loopBody, updateBs);
        } else {
            this.handleSyntaxError("require array type or iterable type", ctx.expression());
            loopStmt = null;
        }
    }
    popBlock();
    if (loopStmt != null)
        block.statements.add(loopStmt);
    return block;
}
Also used : ConstExpr(kalang.ast.ConstExpr) LoopStmt(kalang.ast.LoopStmt) BlockStmt(kalang.ast.BlockStmt) ArrayLengthExpr(kalang.ast.ArrayLengthExpr) AssignExpr(kalang.ast.AssignExpr) ExprNode(kalang.ast.ExprNode) ArrayType(kalang.core.ArrayType) ObjectType(kalang.core.ObjectType) WildcardType(kalang.core.WildcardType) ArrayType(kalang.core.ArrayType) ClassType(kalang.core.ClassType) PrimitiveType(kalang.core.PrimitiveType) Type(kalang.core.Type) GenericType(kalang.core.GenericType) ObjectType(kalang.core.ObjectType) ExprStmt(kalang.ast.ExprStmt) CompareExpr(kalang.ast.CompareExpr) VarDeclStmt(kalang.ast.VarDeclStmt) ObjectInvokeExpr(kalang.ast.ObjectInvokeExpr) PrimitiveCastExpr(kalang.ast.PrimitiveCastExpr) CastExpr(kalang.ast.CastExpr) VarExpr(kalang.ast.VarExpr) TerminalNode(org.antlr.v4.runtime.tree.TerminalNode) LocalVarNode(kalang.ast.LocalVarNode) MethodNotFoundException(kalang.MethodNotFoundException) MathExpr(kalang.ast.MathExpr) ElementExpr(kalang.ast.ElementExpr) AmbiguousMethodException(kalang.AmbiguousMethodException)

Example 4 with MathExpr

use of kalang.ast.MathExpr in project kalang by kasonyang.

the class AstBuilder method createBinaryExpr.

private BinaryExpr createBinaryExpr(ExprNode expr1, ExprNode expr2, String op) {
    BinaryExpr binExpr;
    switch(op) {
        case "==":
        case "!=":
        case ">":
        case ">=":
        case "<":
        case "<=":
            binExpr = new CompareExpr(expr1, expr2, op);
            break;
        case "&&":
        case "||":
            binExpr = new LogicExpr(expr1, expr2, op);
            break;
        default:
            binExpr = new MathExpr(expr1, expr2, op);
            break;
    }
    semanticAnalyzer.validateBinaryExpr(binExpr);
    return binExpr;
}
Also used : CompareExpr(kalang.ast.CompareExpr) LogicExpr(kalang.ast.LogicExpr) BinaryExpr(kalang.ast.BinaryExpr) MathExpr(kalang.ast.MathExpr)

Aggregations

MathExpr (kalang.ast.MathExpr)4 AssignExpr (kalang.ast.AssignExpr)3 CompareExpr (kalang.ast.CompareExpr)3 ConstExpr (kalang.ast.ConstExpr)3 ArrayType (kalang.core.ArrayType)3 ClassType (kalang.core.ClassType)3 GenericType (kalang.core.GenericType)3 ObjectType (kalang.core.ObjectType)3 PrimitiveType (kalang.core.PrimitiveType)3 Type (kalang.core.Type)3 WildcardType (kalang.core.WildcardType)3 ArrayLengthExpr (kalang.ast.ArrayLengthExpr)2 BinaryExpr (kalang.ast.BinaryExpr)2 BlockStmt (kalang.ast.BlockStmt)2 ElementExpr (kalang.ast.ElementExpr)2 ExprNode (kalang.ast.ExprNode)2 ExprStmt (kalang.ast.ExprStmt)2 LocalVarNode (kalang.ast.LocalVarNode)2 LoopStmt (kalang.ast.LoopStmt)2 VarDeclStmt (kalang.ast.VarDeclStmt)2