1 (* Copyright (C) 2009 Matthew Fluet.
2 * Copyright (C) 1999-2008 Henry Cejtin, Matthew Fluet, Suresh
3 * Jagannathan, and Stephen Weeks.
4 * Copyright (C) 1997-2000 NEC Research Institute.
6 * MLton is released under a BSD-style license.
7 * See the file MLton-LICENSE for details.
10 functor x86MLtonBasic (S: X86_MLTON_BASIC_STRUCTS): X86_MLTON_BASIC =
19 structure CType = CType
20 structure Runtime = Runtime
24 * x86.Size.t equivalents
26 val wordBytes = Bytes.toInt Bytes.inWord32
27 val wordSize = Size.fromBytes wordBytes
28 val wordScale = Scale.fromBytes wordBytes
29 val pointerBytes = Bytes.toInt Bytes.inWord32
30 val pointerSize = Size.fromBytes pointerBytes
38 fun new s = MemLoc.Class.new {name = s}
41 val Stack = new "Stack"
42 val Locals = new "Locals"
43 val Globals = new "Globals"
45 val Temp = MemLoc.Class.Temp
46 val StaticTemp = MemLoc.Class.StaticTemp
47 val CStack = MemLoc.Class.CStack
48 val Code = MemLoc.Class.Code
50 val CStatic = new "CStatic"
51 val StaticNonTemp = new "StaticNonTemp"
53 val GCState = new "GCState"
54 val GCStateHold = new "GCStateHold"
55 val GCStateVolatile = new "GCStateVolatile"
58 val allClasses = ref x86.ClassSet.empty
59 val livenessClasses = ref x86.ClassSet.empty
60 val holdClasses = ref x86.ClassSet.empty
61 val volatileClasses = ref x86.ClassSet.empty
62 val runtimeClasses = ref x86.ClassSet.empty
63 val heapClasses = ref x86.ClassSet.empty
64 val cstaticClasses = ref x86.ClassSet.empty
86 val _ = livenessClasses :=
87 (if !Control.Native.liveStack
88 then x86.ClassSet.fromList
95 else x86.ClassSet.fromList
102 val _ = holdClasses :=
103 x86.ClassSet.fromList
111 val _ = volatileClasses :=
112 x86.ClassSet.fromList
117 val _ = runtimeClasses :=
118 x86.ClassSet.fromList
128 val _ = heapClasses :=
129 x86.ClassSet.fromList
134 val _ = cstaticClasses :=
135 x86.ClassSet.fromList
144 val makeContents = x86.MemLoc.makeContents
145 val c_stackP = Label.fromString "c_stackP"
147 = makeContents {base = Immediate.label c_stackP,
149 class = Classes.StaticNonTemp}
150 val c_stackPContentsOperand
151 = Operand.memloc c_stackPContents
152 val c_stackPDerefDouble
153 = MemLoc.simple {base = c_stackPContents,
154 index = Immediate.zero,
157 class = Classes.CStack}
158 val c_stackPDerefDoubleOperand
159 = Operand.memloc c_stackPDerefDouble
160 val c_stackPDerefFloat
161 = MemLoc.simple {base = c_stackPContents,
162 index = Immediate.zero,
165 class = Classes.CStack}
166 val c_stackPDerefFloatOperand
167 = Operand.memloc c_stackPDerefFloat
169 (* This is more a pseudo-location. The GOT is special and cannot
170 * be simply loaded. Similarly, we don't really read the contents.
172 val globalOffsetTable = Label.fromString "_GLOBAL_OFFSET_TABLE_"
173 val globalOffsetTableContents
174 = makeContents {base = Immediate.label globalOffsetTable,
176 class = Classes.StaticNonTemp}
178 val applyFFTempFun = Label.fromString "applyFFTempFun"
179 val applyFFTempFunContents
180 = makeContents {base = Immediate.label applyFFTempFun,
182 class = Classes.StaticTemp}
183 val applyFFTempFunContentsOperand
184 = Operand.memloc applyFFTempFunContents
185 val applyFFTempArg = Label.fromString "applyFFTempArg"
186 val applyFFTempArgContents
187 = makeContents {base = Immediate.label applyFFTempArg,
189 class = Classes.StaticTemp}
190 val applyFFTempArgContentsOperand
191 = Operand.memloc applyFFTempArgContents
193 val realTemp1D = Label.fromString "realTemp1D"
194 val realTemp1ContentsD
195 = makeContents {base = Immediate.label realTemp1D,
197 class = Classes.StaticTemp}
198 val realTemp1ContentsOperandD
199 = Operand.memloc realTemp1ContentsD
200 val realTemp1S = Label.fromString "realTemp1S"
201 val realTemp1ContentsS
202 = makeContents {base = Immediate.label realTemp1S,
204 class = Classes.StaticTemp}
205 val realTemp1ContentsOperandS
206 = Operand.memloc realTemp1ContentsS
207 fun realTemp1ContentsOperand floatSize
209 Size.DBLE => realTemp1ContentsOperandD
210 | Size.SNGL => realTemp1ContentsOperandS
211 | _ => Error.bug "x86MLtonBasic.realTemp1ContentsOperand: floatSize"
213 val realTemp2D = Label.fromString "realTemp2D"
214 val realTemp2ContentsD
215 = makeContents {base = Immediate.label realTemp2D,
217 class = Classes.StaticTemp}
218 val realTemp2ContentsOperandD
219 = Operand.memloc realTemp2ContentsD
220 val realTemp2S = Label.fromString "realTemp2S"
221 val realTemp2ContentsS
222 = makeContents {base = Immediate.label realTemp2S,
224 class = Classes.StaticTemp}
225 val realTemp2ContentsOperandS
226 = Operand.memloc realTemp2ContentsS
227 fun realTemp2ContentsOperand floatSize
229 Size.DBLE => realTemp2ContentsOperandD
230 | Size.SNGL => realTemp2ContentsOperandS
231 | _ => Error.bug "x86MLtonBasic.realTemp2ContentsOperand: floatSize"
233 val realTemp3D = Label.fromString "realTemp3D"
234 val realTemp3ContentsD
235 = makeContents {base = Immediate.label realTemp3D,
237 class = Classes.StaticTemp}
238 val realTemp3ContentsOperandD
239 = Operand.memloc realTemp3ContentsD
240 val realTemp3S = Label.fromString "realTemp3S"
241 val realTemp3ContentsS
242 = makeContents {base = Immediate.label realTemp3S,
244 class = Classes.StaticTemp}
245 val realTemp3ContentsOperandS
246 = Operand.memloc realTemp3ContentsS
247 fun realTemp3ContentsOperand floatSize
249 Size.DBLE => realTemp3ContentsOperandD
250 | Size.SNGL => realTemp3ContentsOperandS
251 | _ => Error.bug "x86MLtonBasic.realTemp3ContentsOperand: floatSize"
253 val fpswTemp = Label.fromString "fpswTemp"
255 = makeContents {base = Immediate.label fpswTemp,
257 class = Classes.StaticTemp}
258 val fpswTempContentsOperand
259 = Operand.memloc fpswTempContents
260 val fildTemp = Label.fromString "fildTemp"
262 = makeContents {base = Immediate.label fildTemp,
264 class = Classes.StaticTemp}
265 val fildTempContentsOperand
266 = Operand.memloc fildTempContents
268 val wordTemp1B = Label.fromString "wordTemp1B"
269 val wordTemp1ContentsB
270 = makeContents {base = Immediate.label wordTemp1B,
272 class = Classes.StaticTemp}
273 val wordTemp1ContentsOperandB
274 = Operand.memloc wordTemp1ContentsB
275 val wordTemp1W = Label.fromString "wordTemp1W"
276 val wordTemp1ContentsW
277 = makeContents {base = Immediate.label wordTemp1W,
279 class = Classes.StaticTemp}
280 val wordTemp1ContentsOperandW
281 = Operand.memloc wordTemp1ContentsW
282 val wordTemp1L = Label.fromString "wordTemp1L"
283 val wordTemp1ContentsL
284 = makeContents {base = Immediate.label wordTemp1L,
286 class = Classes.StaticTemp}
287 val wordTemp1ContentsOperandL
288 = Operand.memloc wordTemp1ContentsL
289 fun wordTemp1ContentsOperand wordSize
291 Size.BYTE => wordTemp1ContentsOperandB
292 | Size.WORD => wordTemp1ContentsOperandW
293 | Size.LONG => wordTemp1ContentsOperandL
294 | _ => Error.bug "x86MLtonBasic.wordTemp1ContentsOperand: wordSize"
299 fun make name size = Label.fromString (concat [prefix, name, size])
302 datatype z = datatype CType.t
307 CPointer => Label.fromString (concat [prefix, "CPointer"])
312 | Objptr => Label.fromString (concat [prefix, "Objptr"])
321 val local_base = make "local"
322 val global_base = make "global"
325 val globalObjptrNonRoot_base = Label.fromString "globalObjptrNonRoot"
327 val gcState_label = Label.fromString "gcState"
329 structure Field = Runtime.GCField
330 fun make' (offset: int, size, class) =
333 Immediate.labelPlusInt
334 (gcState_label, offset)
336 makeContents {base = imm (),
339 fun operand () = Operand.memloc (contents ())
341 (imm, contents, operand)
343 fun make (f: Field.t, size, class) =
346 Immediate.labelPlusInt
347 (gcState_label, Bytes.toInt (Field.offset f))
349 makeContents {base = imm (),
352 fun operand () = Operand.memloc (contents ())
354 (imm, contents, operand)
357 val (_, gcState_exnStackContents,
358 gcState_exnStackContentsOperand) =
359 make (Field.ExnStack, wordSize, Classes.GCState)
361 val (_, gcState_frontierContents,
362 gcState_frontierContentsOperand) =
363 make (Field.Frontier, pointerSize, Classes.GCStateHold)
365 val (_, gcState_stackBottomContents,
366 gcState_stackBottomContentsOperand) =
367 make (Field.StackBottom, pointerSize, Classes.GCState)
369 val (_, gcState_stackTopContents,
370 gcState_stackTopContentsOperand) =
371 make (Field.StackTop, pointerSize, Classes.GCStateHold)
375 Immediate.label (Label.fromString "stackTopTemp")
376 val stackTopTempContents =
377 makeContents {base = stackTopTemp,
379 class = Classes.StaticTemp}
380 val stackTopTempContentsOperand =
381 Operand.memloc (stackTopTempContents)
383 val stackTopTempContents = fn () => stackTopTempContents
384 val stackTopTempContentsOperand = fn () => stackTopTempContentsOperand
387 fun gcState_stackTopMinusWordDeref () =
388 MemLoc.simple {base = gcState_stackTopContents (),
389 index = Immediate.int ~1,
392 class = Classes.Stack}
393 fun gcState_stackTopMinusWordDerefOperand () =
394 Operand.memloc (gcState_stackTopMinusWordDeref ())
396 fun stackTopTempMinusWordDeref () =
397 MemLoc.simple {base = stackTopTempContents (),
398 index = Immediate.int ~1,
401 class = Classes.Stack}
402 fun stackTopTempMinusWordDerefOperand () =
403 Operand.memloc (stackTopTempMinusWordDeref ())
405 fun gcState_offset {offset, ty} =
408 make' (offset, Vector.sub(x86.Size.fromCType ty, 0), Classes.GCState)
415 val _ = Classes.initClasses ()