private void atIfStmnt(Stmnt st) throws CompileError { ASTree expr = st.head(); Stmnt thenp = (Stmnt)st.tail().head(); Stmnt elsep = (Stmnt)st.tail().tail().head(); if (compileBooleanExpr(false, expr)) { hasReturned = false; if (elsep != null) elsep.accept(this); thenp.accept(this); elsep.accept(this); if (!thenHasReturned) bytecode.write16bit(pc2, bytecode.currentPc() - pc2 + 1);
protected void atTryStmnt(Stmnt st) throws CompileError { Bytecode bc = bytecode; Stmnt body = (Stmnt)st.getLeft(); if (body == null) return; ASTList catchList = (ASTList)st.getRight().getLeft(); Stmnt finallyBlock = (Stmnt)st.getRight().getRight().getLeft(); ArrayList gotoList = new ArrayList(); body.accept(this); int end = bc.currentPc(); if (start == end) hasReturned = false; if (block != null) block.accept(this); bc.addAstore(var); hasReturned = false; finallyBlock.accept(this); if (!hasReturned) { bc.addAload(var); if (finallyBlock != null) { if (tryNotReturn) finallyBlock.accept(this);
private boolean needsSuperCall(Stmnt body) throws CompileError { if (body.getOperator() == BLOCK) body = (Stmnt)body.head(); if (body != null && body.getOperator() == EXPR) { ASTree expr = body.head(); if (expr != null && expr instanceof Expr && ((Expr)expr).getOperator() == CALL) { ASTree target = ((Expr)expr).head(); if (target instanceof Keyword) { int token = ((Keyword)target).get(); return token != THIS && token != SUPER; } } } return true; }
private Stmnt parseSwitchBlock(SymbolTable tbl) throws CompileError { if (lex.get() != '{') throw new SyntaxError(lex); SymbolTable tbl2 = new SymbolTable(tbl); Stmnt s = parseStmntOrCase(tbl2); if (s == null) throw new CompileError("empty switch block", lex); int op = s.getOperator(); if (op != CASE && op != DEFAULT) throw new CompileError("no case or default in a switch block", lex); Stmnt body = new Stmnt(BLOCK, s); while (lex.lookAhead() != '}') { Stmnt s2 = parseStmntOrCase(tbl2); if (s2 != null) { int op2 = s2.getOperator(); if (op2 == CASE || op2 == DEFAULT) { body = (Stmnt)ASTList.concat(body, new Stmnt(BLOCK, s2)); s = s2; } else s = (Stmnt)ASTList.concat(s, new Stmnt(BLOCK, s2)); } } lex.get(); // '}' return body; }
private void atSwitchStmnt(Stmnt st) throws CompileError { compileExpr(st.head()); bytecode.add(0); Stmnt body = (Stmnt)st.tail(); int npairs = 0; for (ASTList list = body; list != null; list = list.tail()) if (((Stmnt)list.head()).getOperator() == CASE) ++npairs; for (ASTList list = body; list != null; list = list.tail()) { Stmnt label = (Stmnt)list.head(); int op = label.getOperator(); if (op == DEFAULT) defaultPc = bytecode.currentPc(); else { pairs[ipairs++] = ((long)computeLabel(label.head()) << 32) + ((long)(bytecode.currentPc() - opcodePc) & 0xffffffff); ((Stmnt)label.tail()).accept(this);
protected void atReturnStmnt(Stmnt st) throws CompileError { atReturnStmnt2(st.getLeft()); }
return; // empty int op = st.getOperator(); if (op == EXPR) { ASTree expr = st.getLeft(); doTypeCheck(expr); if (expr instanceof AssignExpr)
private Stmnt parseTry(SymbolTable tbl) throws CompileError { lex.get(); // TRY Stmnt block = parseBlock(tbl); ASTList catchList = null; while (lex.lookAhead() == CATCH) { lex.get(); // CATCH if (lex.get() != '(') throw new SyntaxError(lex); SymbolTable tbl2 = new SymbolTable(tbl); Declarator d = parseFormalParam(tbl2); if (d.getArrayDim() > 0 || d.getType() != CLASS) throw new SyntaxError(lex); if (lex.get() != ')') throw new SyntaxError(lex); Stmnt b = parseBlock(tbl2); catchList = ASTList.append(catchList, new Pair(d, b)); } Stmnt finallyBlock = null; if (lex.lookAhead() == FINALLY) { lex.get(); // FINALLY finallyBlock = parseBlock(tbl); } return Stmnt.make(TRY, block, catchList, finallyBlock); }
/** * Adds a finally clause for earch return statement. */ private void addFinally(ArrayList returnList, Stmnt finallyBlock) throws CompileError { Bytecode bc = bytecode; int n = returnList.size(); for (int i = 0; i < n; ++i) { final int[] ret = (int[])returnList.get(i); int pc = ret[0]; bc.write16bit(pc, bc.currentPc() - pc + 1); ReturnHook hook = new JsrHook2(this, ret); finallyBlock.accept(this); hook.remove(this); if (!hasReturned) { bc.addOpcode(Opcode.GOTO); bc.addIndex(pc + 3 - bc.currentPc()); } } }
private void atBreakStmnt(Stmnt st, boolean notCont) throws CompileError { if (st.head() != null) throw new CompileError( "sorry, not support labeled break or continue"); bytecode.addOpcode(Opcode.GOTO); Integer pc = new Integer(bytecode.currentPc()); bytecode.addIndex(0); if (notCont) breakList.add(pc); else continueList.add(pc); }
private void atSwitchStmnt(Stmnt st) throws CompileError { compileExpr(st.head()); bytecode.add(0); Stmnt body = (Stmnt)st.tail(); int npairs = 0; for (ASTList list = body; list != null; list = list.tail()) if (((Stmnt)list.head()).getOperator() == CASE) ++npairs; for (ASTList list = body; list != null; list = list.tail()) { Stmnt label = (Stmnt)list.head(); int op = label.getOperator(); if (op == DEFAULT) defaultPc = bytecode.currentPc(); else { pairs[ipairs++] = ((long)computeLabel(label.head()) << 32) + ((long)(bytecode.currentPc() - opcodePc) & 0xffffffff); ((Stmnt)label.tail()).accept(this);
private boolean needsSuperCall(Stmnt body) throws CompileError { if (body.getOperator() == BLOCK) body = (Stmnt)body.head(); if (body != null && body.getOperator() == EXPR) { ASTree expr = body.head(); if (expr != null && expr instanceof Expr && ((Expr)expr).getOperator() == CALL) { ASTree target = ((Expr)expr).head(); if (target instanceof Keyword) { int token = ((Keyword)target).get(); return token != THIS && token != SUPER; } } } return true; }
private Stmnt parseSwitchBlock(SymbolTable tbl) throws CompileError { if (lex.get() != '{') throw new SyntaxError(lex); SymbolTable tbl2 = new SymbolTable(tbl); Stmnt s = parseStmntOrCase(tbl2); if (s == null) throw new CompileError("empty switch block", lex); int op = s.getOperator(); if (op != CASE && op != DEFAULT) throw new CompileError("no case or default in a switch block", lex); Stmnt body = new Stmnt(BLOCK, s); while (lex.lookAhead() != '}') { Stmnt s2 = parseStmntOrCase(tbl2); if (s2 != null) { int op2 = s2.getOperator(); if (op2 == CASE || op2 == DEFAULT) { body = (Stmnt)ASTList.concat(body, new Stmnt(BLOCK, s2)); s = s2; } else s = (Stmnt)ASTList.concat(s, new Stmnt(BLOCK, s2)); } } lex.get(); // '}' return body; }
public static Stmnt make(int op, ASTree oprand1, ASTree oprand2) { return new Stmnt(op, oprand1, new ASTList(oprand2)); }
protected void atReturnStmnt(Stmnt st) throws CompileError { atReturnStmnt2(st.getLeft()); }
return; // empty int op = st.getOperator(); if (op == EXPR) { ASTree expr = st.getLeft(); doTypeCheck(expr); if (expr instanceof AssignExpr)