diff options
Diffstat (limited to 'compiler/GHC/CmmToAsm/SPARC/Imm.hs')
-rw-r--r-- | compiler/GHC/CmmToAsm/SPARC/Imm.hs | 67 |
1 files changed, 67 insertions, 0 deletions
diff --git a/compiler/GHC/CmmToAsm/SPARC/Imm.hs b/compiler/GHC/CmmToAsm/SPARC/Imm.hs new file mode 100644 index 0000000000..71b0257ac5 --- /dev/null +++ b/compiler/GHC/CmmToAsm/SPARC/Imm.hs @@ -0,0 +1,67 @@ +module GHC.CmmToAsm.SPARC.Imm ( + -- immediate values + Imm(..), + strImmLit, + litToImm +) + +where + +import GhcPrelude + +import GHC.Cmm +import GHC.Cmm.CLabel + +import Outputable + +-- | An immediate value. +-- Not all of these are directly representable by the machine. +-- Things like ImmLit are slurped out and put in a data segment instead. +-- +data Imm + = ImmInt Int + + -- Sigh. + | ImmInteger Integer + + -- AbstractC Label (with baggage) + | ImmCLbl CLabel + + -- Simple string + | ImmLit SDoc + | ImmIndex CLabel Int + | ImmFloat Rational + | ImmDouble Rational + + | ImmConstantSum Imm Imm + | ImmConstantDiff Imm Imm + + | LO Imm + | HI Imm + + +-- | Create a ImmLit containing this string. +strImmLit :: String -> Imm +strImmLit s = ImmLit (text s) + + +-- | Convert a CmmLit to an Imm. +-- Narrow to the width: a CmmInt might be out of +-- range, but we assume that ImmInteger only contains +-- in-range values. A signed value should be fine here. +-- +litToImm :: CmmLit -> Imm +litToImm lit + = case lit of + CmmInt i w -> ImmInteger (narrowS w i) + CmmFloat f W32 -> ImmFloat f + CmmFloat f W64 -> ImmDouble f + CmmLabel l -> ImmCLbl l + CmmLabelOff l off -> ImmIndex l off + + CmmLabelDiffOff l1 l2 off _ + -> ImmConstantSum + (ImmConstantDiff (ImmCLbl l1) (ImmCLbl l2)) + (ImmInt off) + + _ -> panic "SPARC.Regs.litToImm: no match" |