f059a7b3a8bba25f402178a9954a0cb068a58e42
[ghc.git] / compiler / cmm / Cmm.hs
1 -- Cmm representations using Hoopl's Graph CmmNode e x.
2 {-# LANGUAGE GADTs #-}
3
4 module Cmm (
5 -- * Cmm top-level datatypes
6 CmmProgram, CmmGroup, GenCmmGroup,
7 CmmDecl, GenCmmDecl(..),
8 CmmGraph, GenCmmGraph(..),
9 CmmBlock,
10 RawCmmDecl, RawCmmGroup,
11 Section(..), SectionType(..), CmmStatics(..), CmmStatic(..),
12 isSecConstant,
13
14 -- ** Blocks containing lists
15 GenBasicBlock(..), blockId,
16 ListGraph(..), pprBBlock,
17
18 -- * Info Tables
19 CmmTopInfo(..), CmmStackInfo(..), CmmInfoTable(..), topInfoTable,
20 ClosureTypeInfo(..),
21 ProfilingInfo(..), ConstrDescription,
22
23 -- * Statements, expressions and types
24 module CmmNode,
25 module CmmExpr,
26 ) where
27
28 import GhcPrelude
29
30 import CLabel
31 import BlockId
32 import CmmNode
33 import SMRep
34 import CmmExpr
35 import Hoopl.Block
36 import Hoopl.Collections
37 import Hoopl.Graph
38 import Hoopl.Label
39 import Outputable
40
41 import Data.Word ( Word8 )
42
43 -----------------------------------------------------------------------------
44 -- Cmm, GenCmm
45 -----------------------------------------------------------------------------
46
47 -- A CmmProgram is a list of CmmGroups
48 -- A CmmGroup is a list of top-level declarations
49
50 -- When object-splitting is on, each group is compiled into a separate
51 -- .o file. So typically we put closely related stuff in a CmmGroup.
52 -- Section-splitting follows suit and makes one .text subsection for each
53 -- CmmGroup.
54
55 type CmmProgram = [CmmGroup]
56
57 type GenCmmGroup d h g = [GenCmmDecl d h g]
58 type CmmGroup = GenCmmGroup CmmStatics CmmTopInfo CmmGraph
59 type RawCmmGroup = GenCmmGroup CmmStatics (LabelMap CmmStatics) CmmGraph
60
61 -----------------------------------------------------------------------------
62 -- CmmDecl, GenCmmDecl
63 -----------------------------------------------------------------------------
64
65 -- GenCmmDecl is abstracted over
66 -- d, the type of static data elements in CmmData
67 -- h, the static info preceding the code of a CmmProc
68 -- g, the control-flow graph of a CmmProc
69 --
70 -- We expect there to be two main instances of this type:
71 -- (a) C--, i.e. populated with various C-- constructs
72 -- (b) Native code, populated with data/instructions
73
74 -- | A top-level chunk, abstracted over the type of the contents of
75 -- the basic blocks (Cmm or instructions are the likely instantiations).
76 data GenCmmDecl d h g
77 = CmmProc -- A procedure
78 h -- Extra header such as the info table
79 CLabel -- Entry label
80 [GlobalReg] -- Registers live on entry. Note that the set of live
81 -- registers will be correct in generated C-- code, but
82 -- not in hand-written C-- code. However,
83 -- splitAtProcPoints calculates correct liveness
84 -- information for CmmProcs.
85 g -- Control-flow graph for the procedure's code
86
87 | CmmData -- Static data
88 Section
89 d
90
91 type CmmDecl = GenCmmDecl CmmStatics CmmTopInfo CmmGraph
92
93 type RawCmmDecl
94 = GenCmmDecl
95 CmmStatics
96 (LabelMap CmmStatics)
97 CmmGraph
98
99 -----------------------------------------------------------------------------
100 -- Graphs
101 -----------------------------------------------------------------------------
102
103 type CmmGraph = GenCmmGraph CmmNode
104 data GenCmmGraph n = CmmGraph { g_entry :: BlockId, g_graph :: Graph n C C }
105 type CmmBlock = Block CmmNode C C
106
107 -----------------------------------------------------------------------------
108 -- Info Tables
109 -----------------------------------------------------------------------------
110
111 data CmmTopInfo = TopInfo { info_tbls :: LabelMap CmmInfoTable
112 , stack_info :: CmmStackInfo }
113
114 topInfoTable :: GenCmmDecl a CmmTopInfo (GenCmmGraph n) -> Maybe CmmInfoTable
115 topInfoTable (CmmProc infos _ _ g) = mapLookup (g_entry g) (info_tbls infos)
116 topInfoTable _ = Nothing
117
118 data CmmStackInfo
119 = StackInfo {
120 arg_space :: ByteOff,
121 -- number of bytes of arguments on the stack on entry to the
122 -- the proc. This is filled in by StgCmm.codeGen, and used
123 -- by the stack allocator later.
124 updfr_space :: Maybe ByteOff,
125 -- XXX: this never contains anything useful, but it should.
126 -- See comment in CmmLayoutStack.
127 do_layout :: Bool
128 -- Do automatic stack layout for this proc. This is
129 -- True for all code generated by the code generator,
130 -- but is occasionally False for hand-written Cmm where
131 -- we want to do the stack manipulation manually.
132 }
133
134 -- | Info table as a haskell data type
135 data CmmInfoTable
136 = CmmInfoTable {
137 cit_lbl :: CLabel, -- Info table label
138 cit_rep :: SMRep,
139 cit_prof :: ProfilingInfo,
140 cit_srt :: Maybe CLabel -- empty, or a closure address
141 }
142
143 data ProfilingInfo
144 = NoProfilingInfo
145 | ProfilingInfo [Word8] [Word8] -- closure_type, closure_desc
146
147 -----------------------------------------------------------------------------
148 -- Static Data
149 -----------------------------------------------------------------------------
150
151 data SectionType
152 = Text
153 | Data
154 | ReadOnlyData
155 | RelocatableReadOnlyData
156 | UninitialisedData
157 | ReadOnlyData16 -- .rodata.cst16 on x86_64, 16-byte aligned
158 | CString
159 | OtherSection String
160 deriving (Show)
161
162 -- | Should a data in this section be considered constant
163 isSecConstant :: Section -> Bool
164 isSecConstant (Section t _) = case t of
165 Text -> True
166 ReadOnlyData -> True
167 RelocatableReadOnlyData -> True
168 ReadOnlyData16 -> True
169 CString -> True
170 Data -> False
171 UninitialisedData -> False
172 (OtherSection _) -> False
173
174 data Section = Section SectionType CLabel
175
176 data CmmStatic
177 = CmmStaticLit CmmLit
178 -- a literal value, size given by cmmLitRep of the literal.
179 | CmmUninitialised Int
180 -- uninitialised data, N bytes long
181 | CmmString [Word8]
182 -- string of 8-bit values only, not zero terminated.
183
184 data CmmStatics
185 = Statics
186 CLabel -- Label of statics
187 [CmmStatic] -- The static data itself
188
189 -- -----------------------------------------------------------------------------
190 -- Basic blocks consisting of lists
191
192 -- These are used by the LLVM and NCG backends, when populating Cmm
193 -- with lists of instructions.
194
195 data GenBasicBlock i = BasicBlock BlockId [i]
196
197 -- | The branch block id is that of the first block in
198 -- the branch, which is that branch's entry point
199 blockId :: GenBasicBlock i -> BlockId
200 blockId (BasicBlock blk_id _ ) = blk_id
201
202 newtype ListGraph i = ListGraph [GenBasicBlock i]
203
204 instance Outputable instr => Outputable (ListGraph instr) where
205 ppr (ListGraph blocks) = vcat (map ppr blocks)
206
207 instance Outputable instr => Outputable (GenBasicBlock instr) where
208 ppr = pprBBlock
209
210 pprBBlock :: Outputable stmt => GenBasicBlock stmt -> SDoc
211 pprBBlock (BasicBlock ident stmts) =
212 hang (ppr ident <> colon) 4 (vcat (map ppr stmts))
213