def parse_binop_rhs(self, left, min_precedence=0): while True: precedence = _get_precedence(self.curr_token) if precedence < min_precedence: return left op = self.curr_token self.advance() if op.kind == 'AS': right = self.parse_type() else: right = self.parse_unary_expr() next_precedence = _get_precedence(self.curr_token) if precedence < next_precedence: right = self.parse_binop_rhs(right, precedence + 1) if op.kind == 'AS': left = ast.Cast(left, right, loc=op.loc) elif op.kind in ASSIGNMENT_TOKENS: left = ast.Assignment(left, right, op=AUGMENT_ASSIGNMENT_OP[op.kind], loc=op.loc) else: left = ast.BinaryOp(TOKEN_TO_BINOP[op.kind], left, right, loc=op.loc)
def test_assignment(): root = ast.Block([ ast.Var('foo', ast.IntegerConstant(0), BuiltinTypes.I32), ast.Assignment(ast.Identifier('foo'), ast.IntegerConstant(1)) ]) tp = TypePass() tp.visit(root)
def test_assignment_bad_lvalue(lvalue): root = ast.Block([ ast.Assignment(lvalue, ast.IntegerConstant(1)) ]) tp = TypePass() with pytest.raises(DumbTypeError): tp.visit(root)
def test_assignment_incompatible_types(): root = ast.Block([ ast.Var('foo', ast.IntegerConstant(0), BuiltinTypes.I32), ast.Assignment(ast.Identifier('foo'), ast.FloatConstant(1.0)) ]) tp = TypePass() with pytest.raises(DumbTypeError): tp.visit(root)
def test_augmented_assignment_bad(): root = ast.Block([ ast.Var('foo', ast.IntegerConstant(0), BuiltinTypes.I32), ast.Assignment(ast.Identifier('foo'), ast.IntegerConstant(1), Operator.LOGICAL_OR) ]) tp = TypePass() with pytest.raises(DumbTypeError): tp.visit(root)
def visit_Expression(self, node): raise RuntimeError('Unexpected call.') class StubDeclVisitor(DeclVisitor): def visit_Function(self, node): raise RuntimeError('Unexpected call.') def visit_TranslationUnit(self, node): raise RuntimeError('Unexpected call.') @pytest.mark.parametrize('node', [ ast.BinaryOp(None, None, None), ast.Assignment(None, None), ast.UnaryOp(None, None), ast.Cast(None, None), ast.IntegerConstant(None), ast.FloatConstant(None), ast.BooleanConstant(None), ast.StringConstant(None), ast.Identifier(None), ast.FuncCall(None, None) ]) def test_expr_visitor(node): visitor = StubExprVisitor() method_name = 'visit_' + type(node).__name__ with mock.patch.object(visitor, method_name): visitor.visit(node) getattr(visitor, method_name).assert_called_once_with(node)