def while_statement(token): """ Implements recursive descent for the rule: <while_statement> ==> 34 TokenType.KeywordWhile TokenType.OpenParen <expression> TokenType.CloseParen <code_block> """ if token.t_type == TokenType.KeywordWhile: print(34, end=" ") before_while_lbl, after_while_lbl = CG.gen_label("while") # Write label for beginning of while loop CG.code_gen_label(before_while_lbl) Parser.match(token, TokenType.KeywordWhile) Parser.match(token, TokenType.OpenParen) er_condition = Parser.expression(token) Parser.match(token, TokenType.CloseParen) # Perform the test CG.code_gen_if(er_condition, after_while_lbl) # Write the contents of the loop Parser.code_block(token) # Branch back to the test again CG.code_gen("b", before_while_lbl) # Write label for end of while loop, to pick up when the test fails CG.code_gen_label(after_while_lbl) else: Parser.raise_production_not_found_error(token, 'while_statement')
def if_statement(token): """ Implements recursive descent for the rule: <if_statement> ==> 31 TokenType.KeywordIf TokenType.OpenParen <expression> TokenType.CloseParen <code_block> [ <else_clause> ] """ if token.t_type == TokenType.KeywordIf: print(31, end=" ") Parser.match(token, TokenType.KeywordIf) Parser.match(token, TokenType.OpenParen) er_condition = Parser.expression(token) if er_condition.data_type != DataTypes.BOOL: raise SemanticError( "If statement requires boolean expression " "as an argument", Parser.file_reader.get_line_data()) Parser.match(token, TokenType.CloseParen) else_label, after_else_label = CG.gen_label("else") CG.code_gen_if(er_condition, else_label) Parser.code_block(token) if token.t_type == TokenType.KeywordElse: Parser.match(token, TokenType.KeywordElse) # the last code block must branch to after the else clause CG.code_gen("b", after_else_label) # if test failed, then pick up program execution here CG.code_gen_label(else_label) # generate the else block Parser.code_block(token) # make the after_else label CG.code_gen_label(after_else_label) else: # if test failed, then pick up program execution here CG.code_gen_label(else_label) else: Parser.raise_production_not_found_error(token, 'if_statement')