module SPARC.CodeGen.Base ( InstrBlock, CondCode(..), ChildCode64(..), Amode(..), Register(..), setFormatOfRegister, getRegisterReg, mangleIndexTree ) where import SPARC.Instr import SPARC.Cond import SPARC.AddrMode import SPARC.Regs import Format import Reg import CodeGen.Platform import DynFlags import Cmm import PprCmmExpr () import Platform import Outputable import OrdList -------------------------------------------------------------------------------- -- | 'InstrBlock's are the insn sequences generated by the insn selectors. -- They are really trees of insns to facilitate fast appending, where a -- left-to-right traversal yields the insns in the correct order. -- type InstrBlock = OrdList Instr -- | Condition codes passed up the tree. -- data CondCode = CondCode Bool Cond InstrBlock -- | a.k.a "Register64" -- Reg is the lower 32-bit temporary which contains the result. -- Use getHiVRegFromLo to find the other VRegUnique. -- -- Rules of this simplified insn selection game are therefore that -- the returned Reg may be modified -- data ChildCode64 = ChildCode64 InstrBlock Reg -- | Holds code that references a memory address. data Amode = Amode -- the AddrMode we can use in the instruction -- that does the real load\/store. AddrMode -- other setup code we have to run first before we can use the -- above AddrMode. InstrBlock -------------------------------------------------------------------------------- -- | Code to produce a result into a register. -- If the result must go in a specific register, it comes out as Fixed. -- Otherwise, the parent can decide which register to put it in. -- data Register = Fixed Format Reg InstrBlock | Any Format (Reg -> InstrBlock) -- | Change the format field in a Register. setFormatOfRegister :: Register -> Format -> Register setFormatOfRegister reg format = case reg of Fixed _ reg code -> Fixed format reg code Any _ codefn -> Any format codefn -------------------------------------------------------------------------------- -- | Grab the Reg for a CmmReg getRegisterReg :: Platform -> CmmReg -> Reg getRegisterReg _ (CmmLocal (LocalReg u pk)) = RegVirtual $ mkVirtualReg u (cmmTypeFormat pk) getRegisterReg platform (CmmGlobal mid) = case globalRegMaybe platform mid of Just reg -> RegReal reg Nothing -> pprPanic "SPARC.CodeGen.Base.getRegisterReg: global is in memory" (ppr $ CmmGlobal mid) -- Expand CmmRegOff. ToDo: should we do it this way around, or convert -- CmmExprs into CmmRegOff? mangleIndexTree :: DynFlags -> CmmExpr -> CmmExpr mangleIndexTree dflags (CmmRegOff reg off) = CmmMachOp (MO_Add width) [CmmReg reg, CmmLit (CmmInt (fromIntegral off) width)] where width = typeWidth (cmmRegType dflags reg) mangleIndexTree _ _ = panic "SPARC.CodeGen.Base.mangleIndexTree: no match"