def visit(self, node: cil.DynamicCallNode): meth_offset = self.get_method_index(node.method) dest_address = self.get_address(node.dest) args_space = self.cil_root.get_function( f"{node.type or node.dtype}_{node.method}").args_space if node.type is None: obj_address = self.get_address(node.obj) get_type_inst = ( mips.LWNode( t0, (obj_address, fp)).with_comm("Get instance pointer"), mips.LWNode(t0, (0, t0)).with_comm("Get type pointer at offset 0"), ) else: get_type_inst = (mips.LANode(t0, node.type), ) self.add_inst( mips.CommentNode( f"<dynamiccall:{node.obj}-{node.method}-{node.dest}>"), *get_type_inst, mips.LWNode( t0, (meth_offset, t0)).with_comm(f"Get method: {node.method}"), mips.JALRNode(t0).with_comm(f"Jump to {node.method}"), mips.SWNode(v0, dest_address, fp), mips.ADDINode(sp, sp, args_space).with_comm("Pop args pushed"), mips.CommentNode( f"</dynamiccall:{node.obj}-{node.method}-{node.dest}>"), )
def visit(self, node: cil.ArgNode): address = self.get_address(node.name) self.add_inst( mips.CommentNode(f"<arg:{node.name}>"), mips.LWNode(t0, (address, fp)), mips.ADDINode(sp, sp, -4), mips.SWNode(t0, 0, sp), mips.CommentNode(f"</arg:{node.name}>"), )
def visit(self, node: cil.FunctionNode): params = [x.name for x in node.params] local_vars = [x.name for x in node.local_vars] local_vars_size = len(local_vars) * dw self.cur_function = mips.FunctionNode(node.name, params, local_vars) self.functions[node.name] = self.cur_function # Push local vars push_instructions = (mips.push_register_instructions(ra) + mips.push_register_instructions(fp) + [mips.ADDINode(fp, sp, 8)] + [mips.ADDINode(sp, sp, -local_vars_size)]) self.add_inst( mips.CommentNode(f"<function:{node.name}>"), *push_instructions, ) for instruction in node.instructions: self.visit(instruction) # Pop local vars pop_instructions = ([mips.ADDINode(sp, sp, local_vars_size)] + mips.pop_register_instructions(fp) + mips.pop_register_instructions(ra)) return_instructions = ([mips.LINode(v0, 10), mips.SysCallNode()] if self.cur_function.name == "main" else [mips.JRNode(ra)]) self.add_inst( *pop_instructions, *return_instructions, mips.CommentNode(f"</function:{node.name}>"), )
def visit(self, node: cil.ComplementNode): src = self.get_address(node.src) dest = self.get_address(node.dest) self.add_inst(mips.CommentNode(f"</complement:{node.dest}>"), ) self.visit(cil.StaticCallNode('Int__init', node.dest)) self.add_inst( mips.LWNode(t0, (src, fp)), mips.LWNode(t0, (4, t0)), mips.NOTNode(t0, t0), mips.ADDINode(t0, t0, 1), mips.LWNode(t1, (dest, fp)), mips.SWNode(t0, 4, t1), mips.CommentNode(f"</complement:{node.dest}>"), )
def visit(self, node: cil.TypeNameNode): name_offset = self.types['Object'].name_offset src_offset = self.get_address(node.src) self.add_inst(mips.CommentNode(f"<typename:{node.dest}-{node.src}>"), ) self.visit(cil.StaticCallNode('String__init', node.dest)) self.add_inst( mips.LWNode(t0, (src_offset, fp)).with_comm('Load pointer to self'), mips.LWNode(t0, (0, t0)).with_comm('Load pointer to type of self'), mips.ADDINode(t0, t0, name_offset).with_comm('Point to name of type'), mips.SWNode( t0, 4, v0).with_comm('Save name of the type in the new string'), mips.CommentNode(f"</typename:{node.dest}-{node.src}>"), )