P1 - Quinta 1. a) abstract public class Command { abstract void genC(); } public class ForCommand extends Command { private Variable v; private Expr from, to; private Command command; } public class IfCommand extends Command { private Expr ifExpr; private Command thenCommand, elseCommand; } b) private Command command() { while ( token == Symbol.PRINT || token == Symbol.IDENT || token == Symbol.WHILE || token == Symbol.FOR || token == Symbol.IF || token == Symbol.BEGIN ) switch ( token ) { case Symbol.PRINT: return printCommand(); case Symbol.IDENT: return assignmentCommand(); case Symbol.WHILE: return whileCommand(); case Symbol.FOR: return forCommand(); case Symbol.IF: return ifCommand(); case Symbol.BEGIN: return compositeCommand(); default: error(); return null; } private ForCommand forCommand() { nextToken(); if ( token != Symbol.IDENT ) error(); name = stringValue; nextToken(); Variable v = (Variable ) symbolTable.get(name); if ( v == null ) error(); if ( token != Symbol.ASSIGN ) error(); nextToken(); Expr fromExpr, toExpr; fromExpr = orExpr(); if ( token != Symbol.TO) error(); nextToken(); toExpr = orExpr(); if ( token != Symbol.DO) error(); nextToken(); if ( v.getType() != fromExpr().getType() || v.getType() != toExpr.getType() ) error(); return new ForCommand(v, fromExpr, toExpr); } private IfCommand ifCommand() { Command thenCommand, elseCommand = null; nextToken(); Expr ifExpr = orExpr(); if ( ifExpr.getType() != Type.booleanType ) error(); if ( token != Symbol.THEN ) error(); nextToken(); thenCommand = command(); if ( token == Symbol.ELSE ) { nextToken(); elseCommand = command(); } return new IfCommand(ifExpr, thenCommand, elseCommand); } 2. public class ForCommand extends Command { private Variable v; private Expr from, to; private Command command; static int nextLabel = 1; public void genASM() { /* Em C, a translação seria a seguinte: v = from; while ( v <= to ) command que em assembler é código de from; código do to; pop R1 pop R0 L1: goto> R0, R1, L2 código do comando add R0, 1 goto L1 L2: */ from.genASM(); to.genASM(); sop("pop R1"); sop("pop R0"); int L1 = nextLabel++; int L2 = nextLabel++; sop("L" + L1 + ": goto> R0, R1, L" + L2); command.genASM(); sop("add R0, 1"); sop("goto L" + L1); sop("L" + L2); } }