def AssignmentExpression(self, Subtree): # assign a register AssignRegister = None # get either side LHS = self.Output3AC(Subtree.Left) RHS = self.Output3AC(Subtree.Right) LHSOp = self.GetFormattedOperand(LHS) RHSOp = self.GetFormattedOperand(RHS) # get a register for this assignment expression if type(LHS) is not type("string") and 'float' in LHS['Type']: AssignRegister = FloatRegister.DispenseTicket() else: AssignRegister = IntRegister.DispenseTicket() # outputting binary operation before assignment Ins = self.GetInsFromOp(Subtree.Op) # check for compound operation if Ins is not None: OpA = self.HandleAddress(LHSOp) OpB = self.HandleAddress(RHSOp) self.Load3AC(Instruction=Ins, Dest=AssignRegister, OperandA=OpA, OperandB=OpB) self.Load3AC(Instruction="STORE", Dest=LHSOp, OperandB=AssignRegister) else: self.Load3AC(Instruction="STORE", Dest=LHSOp, OperandB=RHSOp)
def AllocateRegister(self, ID): Register = None if 'float' in ID['Type']: Register = FloatRegister.DispenseTicket() else: Register = IntRegister.DispenseTicket() return Register
def HandleAddress(self, Op): if 'faddr' in Op: Reg = FloatRegister.DispenseTicket() Reg = self.GetFormattedOperand(Reg) self.Load3AC(Instruction="LOAD", Dest=Reg, OperandB=Op) elif 'addr' in Op: Reg = IntRegister.DispenseTicket() Reg = self.GetFormattedOperand(Reg) self.Load3AC(Instruction="LOAD", Dest=Reg, OperandB=Op) else: return Op return Reg
def UnaryExpression(self, Subtree): Op = self.GetInsFromOp(Subtree.Op) RHS = self.GetFormattedOperand(self.Output3AC(Subtree.Child)) AssignRegister = None TypeCheck = self.Output3AC(Subtree.Child) # get a register for this assignment expression if type(TypeCheck) is not type( "string") and 'float' in TypeCheck['Type']: AssignRegister = FloatRegister.DispenseTicket() else: AssignRegister = IntRegister.DispenseTicket() #load into register self.Load3AC(Instruction="LOAD", Dest=AssignRegister, OperandB=RHS) self.Load3AC(Instruction=Op, Dest=AssignRegister, OperandA=AssignRegister, OperandB="const " + str(1)) self.Load3AC(Instruction="RETURN", Dest=RHS, OperandB=AssignRegister)
def CastNode(self, Subtree): # call more 3AC gen after being called CastedReg = self.Output3AC(Subtree.SubExpression) CastType = self.GetTypeString(Subtree.CastTo) # get dest register if 'float' in Subtree.CastTo: CastToReg = FloatRegister.DispenseTicket() else: CastToReg = IntRegister.DispenseTicket() self.Load3AC(Instruction="CONVERT", Dest=CastToReg, OperandA='type ' + CastType, OperandB=CastedReg) return CastToReg
def BinOp(self, Subtree): #base case if not self.IsNode(Subtree): return elif self.IsNodeType(Subtree, "CastNode"): # this wil be replaced with a cast node output thing return self.CastNode(Subtree) elif self.IsNodeType(Subtree, 'ArrayAccess'): return self.ArrayAccess(Subtree) elif self.IsNodeType(Subtree, 'Identifier'): ID = ST_G.RecoverMostRecentID(Subtree.Name) return ID # return data structure elif self.IsNodeType(Subtree, "Constant"): # return pseudo-identifier return { 'Type': [Subtree.DataType], 'Value': Subtree.Child, 'Type Qualifier': ['const'] } elif self.IsNodeType(Subtree, "BinOp"): LHSOp = None RHSOp = None LHS = self.BinOp(Subtree.Left) RHS = self.BinOp(Subtree.Right) # We need to check some things: casts, identifiers for loading into items Ins = self.GetInsFromOp(Subtree.Op) LHSOp = self.GetFormattedOperand(LHS) RHSOp = self.GetFormattedOperand(RHS) if 'faddr' in LHSOp: TempOp = FloatRegister.DispenseTicket() self.Load3AC(Instruction='LOAD', Dest=TempOp, OperandB=LHSOp) LHSOp = TempOp elif 'addr' in LHSOp: TempOp = IntRegister.DispenseTicket() self.Load3AC(Instruction='LOAD', Dest=TempOp, OperandB=LHSOp) LHSOp = TempOp if 'faddr' in RHSOp: TempOp = FloatRegister.DispenseTicket() self.Load3AC(Instruction='LOAD', Dest=TempOp, OperandB=RHSOp) RHSOp = TempOp elif 'addr' in RHSOp: TempOp = IntRegister.DispenseTicket() self.Load3AC(Instruction='LOAD', Dest=TempOp, OperandB=RHSOp) RHSOp = TempOp self.Load3AC(Instruction=Ins, Dest=Subtree.Register, OperandA=LHSOp, OperandB=RHSOp) return Subtree.Register else: for Child in Subtree.GetChildren(): return self.BinOp(Child)