예제 #1
0
    def visitExpr(self, ctx:DecafParser.ExprContext):
                
        if ctx.data_literal():
            if ctx.data_literal().int_literal() != None:
                int_literal = ctx.data_literal().getText()
                self.body += 'movq $' + int_literal + ', %rax\n'
            
        elif ctx.location():
            loc_name = ctx.location().getText()
            location = self.st.lookup(loc_name)

            addr = location.getAddr()

            if location.mem == HEAP:
                self.body += 'movq ' + str(addr) + '(%rbp), %rax\n'
            else:
                self.body += 'movq ' + str(addr) + '(%rsp), %rax\n'

        elif len(ctx.expr()) == 2:
            self.visit(ctx.expr(0))
            self.body += 'movq %rax, %r10\n'

            self.st.stack_pointer[-1] += 8
            self.body += 'movq %r10, ' + str(-self.st.stack_pointer[-1]) + '(%rsp)\n'

            self.visit(ctx.expr(1))
            self.body += 'movq %rax, %r11\n'

            self.body += 'movq ' + str(-self.st.stack_pointer[-1]) + '(%rsp), %r10\n'
            self.st.stack_pointer[-1] -= 8

            if ctx.bin_op().arith_op().ADD():
                self.body += 'addq %r10, %r11\n'
            elif ctx.bin_op().arith_op().SUB():
                self.body += 'subq %r11, %r10\n'
                self.body += 'movq %r10, %r11\n'
            elif ctx.bin_op().arith_op().MUL():
                self.body += 'imul %r10, %r11\n'
            elif ctx.bin_op().arith_op().DIV():
                self.body += 'movq $0, %rdx\n'
                self.body += 'movq %r11, %rbx\n'
                self.body += 'movq %r10, %rax\n'
                self.body += 'idiv %rbx\n'
                self.body += 'movq %rax, %r11\n'

            self.body += 'movq %r11, %rax\n'

        else:
            self.visitChildren(ctx)
예제 #2
0
    def visitExpr(self, ctx: DecafParser.ExprContext):
        line_num = ctx.start.line
        expr_type = ""

        if len(ctx.expr()) == 2:

            type_a = self.visit(ctx.expr(0))
            type_b = self.visit(ctx.expr(1))
            op = ctx.bin_op()

            if type_a == type_b:
                expr_type = type_a

            else:
                expr_type = None
                #print('Error on line', line_num, 'type mismatched in expression')

            #12
            if (op.rel_op() != None or op.arith_op() != None
                ) and type_a != 'int' and type_b != 'int':
                print('Error on line ' + str(line_num) +
                      ' operands must be of type int')
            #13
            elif op.eq_op() != None and type_a != type_b:
                print('Error on line ' + str(line_num) +
                      ' operands must be of same type')
            #14
            elif op.cond_op() != None and (type_a != 'boolean'
                                           or type_b != 'boolean'):
                print('Error on line ' + str(line_num) +
                      ' operands must be of type boolean')

        elif ctx.location() != None:

            var_name = ctx.location().ID().getText()
            var_symbol = self.st.lookup(var_name)

            if var_symbol != None:
                expr_type = var_symbol.type

            else:
                #2
                expr_type = None
                print('Error on line ' + str(line_num) + ', ' + var_name +
                      ' has not been declared')

        elif ctx.data_literal() != None:

            if ctx.data_literal().int_literal() != None:
                expr_type = 'int'

            elif ctx.data_literal().bool_literal() != None:
                expr_type = 'boolean'

            else:
                expr_type = None

        elif ctx.method_call() != None:

            method_name = ctx.method_call().method_name().getText()
            method_symbol = self.st.lookup(method_name)

            if method_symbol != None:

                expr_type = method_symbol.type
                self.visit(ctx.method_call())

            else:
                method_symbol = None

        elif ctx.EXCLAMATION() != None:

            expr_type = self.visit(ctx.expr(0))

            #14
            if expr_type != 'boolean':
                print('Error on line ' + str(line_num) +
                      ' operand must be of type boolean')

        else:
            self.visitChildren(ctx)

        return expr_type