Beispiel #1
0
 def gen(self, frame):
     f = frame.new_label()
     t = frame.new_label()
     temp = frame.alloc_temp(ty.Type.Int)
     self.jumping(0, f, frame)
     const = Constant(lexer.Num(1), ty.Type.Int)
     self.emit(il.Assign(temp, const), frame)
     self.emit(il.Goto(t), frame)
     self.emit_label(f, frame)
     const = Constant(lexer.Num(0), ty.Type.Int)
     self.emit(il.Assign(temp, const), frame)
     self.emit_label(t, frame)
     return temp
Beispiel #2
0
    def _parse_primary_expression(self, env):
        """ <primary_expression>

        Parses the <primary_expression> language structure.

            primary_expression -> 'constant'
                                |   '(' logical_expression ')'
                                |   'identifier'

        """
        token = self._look
        if self._accept(lexer.Tag.NUM):
            return ast.Constant(token, ty.Type.Int)
        elif self._accept(lexer.Tag.NULL):
            return ast.Constant(lexer.Num(0), ty.Type.Int)
        elif self._accept('('):
            logexp = self._parse_logical_expression(env)
            self._match(')')
            return logexp
        self._match(lexer.Tag.ID, 'identifier')
        id_obj = None
        try:
            id_obj = env.find(str(token))
        except errors.ParserNameError as e:
            self._name_error('identifier has not been declared', str(token))
        return id_obj
Beispiel #3
0
    def jumping(self, true_label, false_label, frame):
        """ Generate Expression's Jumping Code

        Arguments:
            true_label: The true branch.
            false_label: The false branch.
        """
        const = Constant(lexer.Num(0), ty.Type.Int)
        self.emitjumps(Rel(lexer.Token('>'), self.reduce(frame), const),
                       true_label, false_label, frame)
Beispiel #4
0
 def reduce(self, frame):
     func_call = self.gen(frame)
     for arg in func_call.get_args():
         self.emit(il.Param(param=arg), frame)
     args_count = len(func_call.get_args())
     const = Constant(lexer.Num(args_count), ty.Type.Int)
     self.emit(il.Call(call=func_call.get_id_expr(), n=const), frame)
     if func_call.get_type() is ty.Type.Void:
         return None
     temp = frame.alloc_temp(func_call.get_type())
     self.emit(il.LoadRet(temp), frame)
     return temp
Beispiel #5
0
    def _parse_array_offset(self, expr, env):
        """
        Parses the array offset.

        """
        self._match('[')
        num = self._parse_logical_expression(env)
        self._match(']')
        of_type = expr.get_type().get_of_type()
        width = ast.Constant(lexer.Num(of_type.get_width()), ty.Type.Int)
        expr_id = expr
        offset = ast.Binary(lexer.Token('*'), num, width)
        if type(expr) is ast.Access:
            expr_id = expr.get_access_id()
            offset = ast.Binary(lexer.Token('+'), expr.get_offset(), offset)
        return ast.Access(lexer.Word('[]', lexer.Tag.INDEX), of_type, expr_id,
                          offset)
Beispiel #6
0
    def _parse_ptr_offset(self, expr):
        """
        Parses the pointer offset.

        """
        self._match(lexer.Tag.PTR)
        token = self._look
        self._match(lexer.Tag.ID)
        struct_type = expr.get_type().get_ref_type()
        struct_field = None
        try:
            struct_field = struct_type.get_identifier_table().find(str(token))
        except errors.ParserNameError:
            self._name_error('struct has no such field', str(token))
        offset = ast.Constant(lexer.Num(struct_field.get_offset()),
                              ty.Type.Int)
        return ast.Access(lexer.Word('->', lexer.Tag.INDEX),
                          struct_field.get_type(), expr, offset)
Beispiel #7
0
def num_parser(token):
    next_token = use_token(token, L.Num)
    return next_token, L.Num(token[0].value)