2 % (c) The GRASP Project, Glasgow University, 1992-1996
4 \section[PrimRep]{Primitive machine-level kinds of things.}
6 At various places in the back end, we want to be to tag things with a
7 ``primitive kind''---i.e., the machine-manipulable implementation
11 #include "HsVersions.h"
16 separateByPtrFollowness, isFollowableRep, isFloatingRep,
17 getPrimRepSize, retPrimRepSize,
18 showPrimRep, ppPrimRep,
19 guessPrimRep, decodePrimRep
24 import Pretty -- pretty-printing code
27 #include "../../includes/GhcConstants.h"
30 %************************************************************************
32 \subsection[PrimRep-datatype]{The @PrimRep@ datatype}
34 %************************************************************************
38 = -- These pointer-kinds are all really the same, but we keep
39 -- them separate for documentation purposes.
40 PtrRep -- Pointer to a closure; a ``word''.
41 | CodePtrRep -- Pointer to code
42 | DataPtrRep -- Pointer to data
43 | RetRep -- Pointer to code or data (return vector or code pointer)
44 | CostCentreRep -- Pointer to a cost centre
46 | CharRep -- Machine characters
47 | IntRep -- integers (at least 32 bits)
48 | WordRep -- ditto (but *unsigned*)
49 | AddrRep -- addresses ("C pointers")
51 | DoubleRep -- doubles
53 | ForeignObjRep -- This has to be a special kind because ccall
54 -- generates special code when passing/returning
55 -- one of these. [ADR]
57 | StablePtrRep -- We could replace this with IntRep but maybe
58 -- there's some documentation gain from having
61 | ArrayRep -- Primitive array of Haskell pointers
62 | ByteArrayRep -- Primitive array of bytes (no Haskell pointers)
64 | VoidRep -- Occupies no space at all!
65 -- (Primitive states are mapped onto this)
67 -- Kinds are used in PrimTyCons, which need both Eq and Ord
70 %************************************************************************
72 \subsection[PrimRep-predicates]{Follow-ness, sizes, and such---on @PrimitiveKinds@}
74 %************************************************************************
76 Whether or not the thing is a pointer that the garbage-collector
79 Or, to put it another (less confusing) way, whether the object in
80 question is a heap object.
83 isFollowableRep :: PrimRep -> Bool
85 isFollowableRep PtrRep = True
86 isFollowableRep ArrayRep = True
87 isFollowableRep ByteArrayRep = True
88 -- why is a ForeignObj followable? 4/96 SOF
90 -- A: they're followable because these objects
91 -- should be lugged around by the storage manager
92 -- (==> we need to generate code that identify them as such) -- 3/97 SOF
93 isFollowableRep ForeignObjRep = True
95 isFollowableRep StablePtrRep = False
96 -- StablePtrs aren't followable because they are just indices into a
97 -- table for which explicit allocation/ deallocation is required.
99 isFollowableRep other = False
101 separateByPtrFollowness :: (a -> PrimRep) -> [a] -> ([a], [a])
103 separateByPtrFollowness kind_fun things
104 = sep_things kind_fun things [] []
105 -- accumulating params for follow-able and don't-follow things...
107 sep_things kfun [] bs us = (reverse bs, reverse us)
108 sep_things kfun (t:ts) bs us
109 = if (isFollowableRep . kfun) t then
110 sep_things kfun ts (t:bs) us
112 sep_things kfun ts bs (t:us)
115 @isFloatingRep@ is used to distinguish @Double@ and @Float@ which
116 cause inadvertent numeric conversions if you aren't jolly careful.
117 See codeGen/CgCon:cgTopRhsCon.
120 isFloatingRep :: PrimRep -> Bool
122 isFloatingRep DoubleRep = True
123 isFloatingRep FloatRep = True
124 isFloatingRep other = False
128 getPrimRepSize :: PrimRep -> Int
130 getPrimRepSize DoubleRep = DOUBLE_SIZE -- "words", of course
131 --getPrimRepSize FloatRep = 1
132 --getPrimRepSize CharRep = 1 -- ToDo: count in bytes?
133 --getPrimRepSize ArrayRep = 1 -- Listed specifically for *documentation*
134 --getPrimRepSize ByteArrayRep = 1
135 getPrimRepSize VoidRep = 0
136 getPrimRepSize other = 1
138 retPrimRepSize = getPrimRepSize RetRep
141 %************************************************************************
143 \subsection[PrimRep-instances]{Boring instance decls for @PrimRep@}
145 %************************************************************************
148 instance Outputable PrimRep where
149 ppr sty kind = ppStr (showPrimRep kind)
151 showPrimRep :: PrimRep -> String
152 -- dumping PrimRep tag for unfoldings
153 ppPrimRep :: PrimRep -> Pretty
155 guessPrimRep :: String -> PrimRep -- a horrible "inverse" function
156 decodePrimRep :: Char -> PrimRep -- of equal nature
164 CostCentreRep -> 'c' -- Pointer to a cost centre
177 _ -> panic "ppPrimRep")
179 showPrimRep PtrRep = "P_" -- short for StgPtr
181 showPrimRep CodePtrRep = "P_" -- DEATH to StgFunPtr! (94/02/22 WDP)
182 -- but aren't code pointers and function pointers different sizes
183 -- on some machines (eg 80x86)? ADR
184 -- Are you trying to ruin my life, or what? (WDP)
186 showPrimRep DataPtrRep = "D_"
187 showPrimRep RetRep = "StgRetAddr"
188 showPrimRep CostCentreRep = "CostCentre"
189 showPrimRep CharRep = "StgChar"
190 showPrimRep IntRep = "I_" -- short for StgInt
191 showPrimRep WordRep = "W_" -- short for StgWord
192 showPrimRep AddrRep = "StgAddr"
193 showPrimRep FloatRep = "StgFloat"
194 showPrimRep DoubleRep = "StgDouble"
195 showPrimRep ArrayRep = "StgArray" -- see comment below
196 showPrimRep ByteArrayRep = "StgByteArray"
197 showPrimRep StablePtrRep = "StgStablePtr"
198 showPrimRep ForeignObjRep = "StgPtr" -- see comment below
199 showPrimRep VoidRep = "!!VOID_KIND!!"
219 _ -> panic "decodePrimRep"
221 guessPrimRep "D_" = DataPtrRep
222 guessPrimRep "StgRetAddr" = RetRep
223 guessPrimRep "StgChar" = CharRep
224 guessPrimRep "I_" = IntRep
225 guessPrimRep "W_" = WordRep
226 guessPrimRep "StgAddr" = AddrRep
227 guessPrimRep "StgFloat" = FloatRep
228 guessPrimRep "StgDouble" = DoubleRep
229 guessPrimRep "StgArray" = ArrayRep
230 guessPrimRep "StgByteArray" = ByteArrayRep
231 guessPrimRep "StgStablePtr" = StablePtrRep
234 All local C variables of @ArrayRep@ are declared in C as type
235 @StgArray@. The coercion to a more precise C type is done just before
236 indexing (by the relevant C primitive-op macro).
238 Nota Bene. There are three types associated with @ForeignObj@ (MallocPtr++):
241 @StgForeignObjClosure@ is the type of the thing the prim. op @mkForeignObj@ returns.
242 {- old comment for MallocPtr
243 (This typename is hardwired into @ppr_casm_results@ in
248 @StgForeignObj@ is the type of the thing we give the C world.
251 @StgPtr@ is the type of the (pointer to the) heap object which we
252 pass around inside the STG machine.
255 It is really easy to confuse the two. (I'm not sure this choice of
256 type names helps.) [ADR]