Home My Page Projects Code Snippets Project Openings SML/NJ
Summary Activity Forums Tracker Lists Tasks Docs Surveys News SCM Files

SCM Repository

[smlnj] Diff of /sml/trunk/src/MLRISC/x86/x86.md
ViewVC logotype

Diff of /sml/trunk/src/MLRISC/x86/x86.md

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

sml/branches/SMLNJ/src/MLRISC/x86/x86.md revision 429, Wed Sep 8 09:47:00 1999 UTC sml/trunk/src/MLRISC/x86/x86.md revision 624, Fri Apr 21 03:06:21 2000 UTC
# Line 27  Line 27 
27       *)       *)
28    
29     storage     storage
30        GP = 32 cells of 32 bits in cellset called "register"        GP "r" = 32 cells of 32 bits in cellset called "register"
31             assembly as             assembly as
32                      (fn 0 => "%eax"                      (fn (0,8)  => "%al"
33                        | 1 => "%ecx"                        | (0,16) => "%ax"
34                        | 2 => "%edx"                        | (0,32) => "%eax"
35                        | 3 => "%ebx"                        | (1,8)  => "%cl"
36                        | 4 => "%esp"                        | (1,16) => "%cx"
37                        | 5 => "%ebp"                        | (1,32) => "%ecx"
38                        | 6 => "%esi"                        | (2,8)  => "%dl"
39                        | 7 => "%edi"                        | (2,16) => "%dx"
40                        | r => "%"^Int.toString r                        | (2,32) => "%edx"
41                          | (3,8)  => "%bl"
42                          | (3,16) => "%bx"
43                          | (3,32) => "%ebx"
44                          | (4,16) => "%sp"
45                          | (4,32) => "%esp"
46                          | (5,16) => "%bp"
47                          | (5,32) => "%ebp"
48                          | (6,16) => "%si"
49                          | (6,32) => "%esi"
50                          | (7,16) => "%di"
51                          | (7,32) => "%edi"
52                          | (r,_) => "%"^Int.toString r
53                      )                      )
54     |  FP = 32 cells of 80 bits in cellset called "floating point register"     |  FP "f" = 32 cells of 80 bits in cellset called "floating point register"
55             assembly as (fn f => if f >= 0 andalso f < 8                 assembly as (fn (0,_) => "%st"
56                                  then "%st("^Int.toString f^")"                               | (f,_) =>
57                                  else "%f"^Int.toString f (* fake register *)                                  if f < 8 then "%st("^Int.toString f^")"
58                                    else "%f"^Int.toString f
59                                         (* pseudo register *)
60                         )                         )
61     |  CC = cells of 32 bits in cellset called "condition code register"     |  CC "cc" = cells of 32 bits in cellset called "condition code register"
62             assembly as "cc"             assembly as "cc"
63       |  MEM "m" = cells of 8 bits called "memory"
64                    assembly as (fn (r,_) => "m"^Int.toString r)
65       |  CTRL "ctrl" = cells of 8 bits called "control"
66                    assembly as (fn (r,_) => "ctrl"^Int.toString r)
67    
68     locations     locations
69         eax     = $GP[0]         eax     = $GP[0]
70     and ecx     = $GP[1]     and ecx     = $GP[1]
# Line 56  Line 75 
75     and esi     = $GP[6]     and esi     = $GP[6]
76     and edi     = $GP[7]     and edi     = $GP[7]
77     and stackptrR = $GP[4]     and stackptrR = $GP[4]
78       and ST(x)   = $FP[x]
79     and asmTmpR   = ~1 (* not used *)     and asmTmpR   = ~1 (* not used *)
80     and fasmTmp   = ~1 (* not used *)     and fasmTmp   = ~1 (* not used *)
81    
82     structure Cells =     structure RTL =
83     struct     struct
       fun zeroReg _ = NONE  
84     end     end
85    
   
    (*  
    semantics X86 =  
    struct  
       include "MD++/basis.md"  
       open Basis  
       structure Int32 = struct type int end  
       type 'a option  
    end *)  
   
86     structure Instruction = struct     structure Instruction = struct
87   (* An effective address can be any combination of   (* An effective address can be any combination of
88    *  base + index*scale + disp    *  base + index*scale + disp
# Line 96  Line 105 
105    (* Note: Relative is only generated after sdi resolution *)    (* Note: Relative is only generated after sdi resolution *)
106    datatype operand =    datatype operand =
107       Immed      of Int32.int       Immed      of Int32.int
    | Const      of Constant.const  
108     | ImmedLabel of LabelExp.labexp     | ImmedLabel of LabelExp.labexp
109     | Relative   of int     | Relative   of int
110     | LabelEA    of LabelExp.labexp     | LabelEA    of LabelExp.labexp
111     | Direct     of $GP     | Direct     of $GP
112     | FDirect    of $FP     | FDirect    of $FP
113       | ST         of $FP
114       | MemReg     of int (* pseudo memory register *)
115     | Displace   of {base: $GP, disp:operand, mem:Region.region}     | Displace   of {base: $GP, disp:operand, mem:Region.region}
116     | Indexed    of {base: $GP option, index: $GP, scale:int, disp:operand,     | Indexed    of {base: $GP option, index: $GP, scale:int, disp:operand,
117                      mem:Region.region}                      mem:Region.region}
118    
119    type ea = operand    type addressing_mode = operand
   
   datatype binaryOp! = ADD | SUB  | AND | OR | XOR | SHL | SAR | SHR  
   
   datatype multDivOp! = UMUL | IDIV | UDIV  
120    
121    datatype unaryOp! = DEC | INC | NEG | NOT    type ea = operand
   
   datatype move! = MOVL | MOVZX | MOVB  
122    
123    datatype cond! =    datatype cond! =
124        EQ | NE | LT | LE | GT | GE        EQ "e" | NE | LT "l" | LE | GT "g" | GE
125      | B  | BE (* below *)   | A  | AE (* above *)      | B  | BE (* below *)   | A  | AE (* above *)
126      | C  | NC (* if carry *)| P  | NP (* if parity *)      | C  | NC (* if carry *)| P  | NP (* if parity *)
127      | O  | NO (* overflow *)      | O  | NO (* overflow *)
128    
129      datatype binaryOp! =
130         ADDL | SUBL | ANDL | ORL | XORL | SHLL | SARL | SHRL | ADCL | SBBL
131       | ADDW | SUBW | ANDW | ORW | XORW | SHLW | SARW | SHRW
132       | ADDB | SUBB | ANDB | ORB | XORB | SHLB | SARB | SHRB
133    
134      datatype multDivOp! = MULL | IDIVL | DIVL
135    
136      datatype unaryOp! = DECL | INCL | NEGL | NOTL | NOTW | NOTB
137    
138      datatype move! = MOVL
139                     | MOVB
140                     | MOVW
141                     | MOVSWL | MOVZWL  (* word -> long *)
142                     | MOVSBL | MOVZBL  (* byte -> long *)
143    
144   (* The Intel manual is incorrect on the description of FDIV and FDIVR *)   (* The Intel manual is incorrect on the description of FDIV and FDIVR *)
145    datatype fbinOp! =    datatype fbinOp! =
146        FADDP  | FADD        FADDP   | FADDS
147      | FMULP  | FMUL      | FMULP   | FMULS
148      | FSUBP  | FSUB             (* ST(1) := ST-ST(1); [pop] *)                | FCOMS
149      | FSUBRP | FSUBR            (* ST(1) := ST(1)-ST; [pop] *)                | FCOMPS
150      | FDIVP  | FDIV             (* ST(1) := ST/ST(1); [pop] *)      | FSUBP   | FSUBS   (* ST(1) := ST-ST(1); [pop] *)
151      | FDIVRP | FDIVR            (* ST(1) := ST(1)/ST; [pop] *)      | FSUBRP  | FSUBRS  (* ST(1) := ST(1)-ST; [pop] *)
152        | FDIVP   | FDIVS   (* ST(1) := ST/ST(1); [pop] *)
153        | FDIVRP  | FDIVRS  (* ST(1) := ST(1)/ST; [pop] *)
154                  | FADDL
155                  | FMULL
156                  | FCOML
157                  | FCOMPL
158                  | FSUBL   (* ST(1) := ST-ST(1); [pop] *)
159                  | FSUBRL  (* ST(1) := ST(1)-ST; [pop] *)
160                  | FDIVL   (* ST(1) := ST/ST(1); [pop] *)
161                  | FDIVRL  (* ST(1) := ST(1)/ST; [pop] *)
162    
163      datatype fibinOp! =
164          FIADDS | FIMULS   | FICOMS | FICOMPS
165        | FISUBS | FISUBRS  | FIDIVS | FIDIVRS
166        | FIADDL | FIMULL   | FICOML | FICOMPL
167        | FISUBL | FISUBRL  | FIDIVL | FIDIVRL
168    
169    datatype funOp! = FABS | FCHS    datatype funOp! = FABS | FCHS
170                      | FSIN | FCOS | FTAN
171                      | FSCALE | FRNDINT | FSQRT
172                      | FTST | FXAM
173                      | FINCSTP | FDECSTP
174    
175      datatype fenvOp! = FLDENV | FNLDENV | FSTENV | FNSTENV
176    
177    end (* struct Instruction *)    end (* struct Instruction *)
178    
179      (*
180       * Instruction encoding on the x86
181       * Because of variable width instructions.
182       * We decompose each byte field into a seperate format first, then combine
183       * then to form the real instructions
184       *)
185      instruction formats 8 bits
186        modrm{mod:2, reg:3, rm:3}
187      | sib{ss:2, index:3, base:3}
188      | immed8{imm:8}
189    
190      instruction formats 32 bits
191        immed32{imm:32}
192    
193    (* A bunch of routines for emitting assembly *)    (* A bunch of routines for emitting assembly *)
194    functor Assembly    functor Assembly
195       (structure MemRegs : MEMORY_REGISTERS where I = Instr) =       (structure MemRegs : MEMORY_REGISTERS where I = Instr) =
# Line 145  Line 200 
200           val s = if i >= 0 then s else "-"^String.substring(s,1,size s-1)           val s = if i >= 0 then s else "-"^String.substring(s,1,size s-1)
201       in  emit s end       in  emit s end
202    
      fun emit_src2 NONE = ()  
        | emit_src2(SOME i) = (emit "$"; emitInt32 i; emit ", ")  
   
203       fun emitScale 0 = emit "1"       fun emitScale 0 = emit "1"
204         | emitScale 1 = emit "2"         | emitScale 1 = emit "2"
205         | emitScale 2 = emit "4"         | emitScale 2 = emit "4"
# Line 155  Line 207 
207         | emitScale _ = error "emitScale"         | emitScale _ = error "emitScale"
208    
209       and eImmed(I.Immed (i)) = emitInt32 i       and eImmed(I.Immed (i)) = emitInt32 i
        | eImmed(I.Const c) = emit_const c  
210         | eImmed(I.ImmedLabel lexp) = emit_labexp lexp         | eImmed(I.ImmedLabel lexp) = emit_labexp lexp
211         | eImmed _ = error "eImmed"         | eImmed _ = error "eImmed"
212    
213       and emit_operand opn =       and emit_operand opn =
214           case opn of           case opn of
215           I.Immed i => (emit "$"; emitInt32 i)           I.Immed i => (emit "$"; emitInt32 i)
        | I.Const c => emit_const c  
216         | I.ImmedLabel lexp => (emit "$"; emit_labexp lexp)         | I.ImmedLabel lexp => (emit "$"; emit_labexp lexp)
217         | I.LabelEA le => emit_labexp le         | I.LabelEA le => emit_labexp le
218         | I.Relative _ => error "emit_operand"         | I.Relative _ => error "emit_operand"
219         | I.Direct r => emit_GP r         | I.Direct r => emit_GP r
220         | I.FDirect f =>         | I.MemReg r => emit_operand(memReg opn)
221              let val f' = regmap f         | I.ST f => emit_FP f
222              in  if f' < (32+8) then emit_FP f' else emit_operand(memReg opn) end         | I.FDirect f => emit_operand(memReg opn)
        | I.Displace{base,disp=I.Immed(0),mem,...} =>  
            (emit "("; emit_GP base; emit ")"; emit_region mem)  
223         | I.Displace{base,disp,mem,...} =>         | I.Displace{base,disp,mem,...} =>
224             (eImmed disp; emit "("; emit_GP base; emit ")";             (emit_disp disp; emit "("; emit_GP base; emit ")";
             emit_region mem)  
        | I.Indexed{base=NONE,index,scale,disp,mem,...} =>  
           (emit "("; emit_GP index; comma(); emitScale scale; emit ")";  
            emit_region mem)  
        | I.Indexed{base=SOME base,index,scale,disp,mem,...} =>  
          (eOptionalDisp disp; emit "("; emit_GP base;  
           comma(); emit_GP index; comma(); emitScale scale; emit ")";  
225            emit_region mem)            emit_region mem)
226        and eOptionalDisp(I.Immed 0) = ()         | I.Indexed{base,index,scale,disp,mem,...} =>
227          | eOptionalDisp(I.Const c) = emit(Constant.toString c)            (emit_disp disp; emit "(";
228          | eOptionalDisp(I.Immed i) = emitInt32 i             case base of
229          | eOptionalDisp _ = error "eOptionalDisp"               NONE => ()
230               | SOME base => emit_GP base;
231               comma();
232               emit_GP index; comma();
233               emitScale scale; emit ")"; emit_region mem)
234    
235          and emit_disp(I.Immed 0) = ()
236            | emit_disp(I.Immed i) = emitInt32 i
237            | emit_disp(I.ImmedLabel lexp) = emit_labexp lexp
238            | emit_disp _ = error "emit_disp"
239    
240       (* The gas assembler does not like the "$" prefix for immediate       (* The gas assembler does not like the "$" prefix for immediate
241        * labels in certain instructions.        * labels in certain instructions.
242        *)        *)
243        fun stupidGas(I.ImmedLabel lexp) = emit_labexp lexp        fun stupidGas(I.ImmedLabel lexp) = emit_labexp lexp
244          | stupidGas(I.LabelEA _) = error "stupidGas"          | stupidGas opnd = (emit "*"; emit_operand opnd)
245          | stupidGas opnd = emit_operand opnd  
246         (* Display the floating point binary opcode *)
247          fun isMemOpnd(I.MemReg _) = true
248            | isMemOpnd(I.FDirect f) = true
249            | isMemOpnd(I.LabelEA _) = true
250            | isMemOpnd(I.Displace _) = true
251            | isMemOpnd(I.Indexed _) = true
252            | isMemOpnd _ = false
253          fun chop fbinOp =
254              let val n = size fbinOp
255              in  case Char.toLower(String.sub(fbinOp,n-1)) of
256                    (#"s" | #"l") => String.substring(fbinOp,0,n-1)
257                  | _ => fbinOp
258              end
259    
260        val emit_dst = emit_operand        val emit_dst = emit_operand
261        val emit_src = emit_operand        val emit_src = emit_operand
262        val emit_opnd = emit_operand        val emit_opnd = emit_operand
       val emit_src1 = emit_operand  
263        val emit_rsrc = emit_operand        val emit_rsrc = emit_operand
264        val emit_lsrc = emit_operand        val emit_lsrc = emit_operand
265        val emit_addr = emit_operand        val emit_addr = emit_operand
266    end        val emit_src1 = emit_operand
267      end (* Instruction *)
268    
269   (* many of these instructions imply certain register usages *)   (* many of these instructions imply certain register usages *)
270    instruction    instruction
# Line 212  Line 275 
275          ``jmp\t<stupidGas operand>''          ``jmp\t<stupidGas operand>''
276    
277      | JCC of {cond:cond, opnd:operand}      | JCC of {cond:cond, opnd:operand}
278          ``j<cond>, <stupidGas opnd>''          ``j<cond>\t<stupidGas opnd>''
279    
280      | CALL of operand * C.cellset * C.cellset * Region.region      | CALL of operand * C.cellset * C.cellset * Region.region
281          ``call\t<stupidGas operand><region>''          ``call\t<stupidGas operand><region><
282              emit_defs(cellset1)><
283              emit_uses(cellset2)>''
284    
285        | ENTER of {src1:operand, src2:operand}
286            ``enter\t<emit_operand src1>, <emit_operand src2>''
287    
288        | LEAVE
289            ``leave''
290    
291      | RET of operand option      | RET of operand option
292          ``ret<case operand of NONE => ()          ``ret<case operand of NONE => ()
# Line 228  Line 299 
299      | LEA of {r32: $GP, addr: operand}      | LEA of {r32: $GP, addr: operand}
300          ``leal\t<addr>, <r32>''          ``leal\t<addr>, <r32>''
301    
302      | CMP of {lsrc: operand, rsrc: operand}      | CMPL of {lsrc: operand, rsrc: operand}
303          ``cmpl\t<rsrc>, <lsrc>''          ``cmpl\t<rsrc>, <lsrc>''
304    
305        | CMPW of {lsrc: operand, rsrc: operand}
306            ``cmpb\t<rsrc>, <lsrc>''
307    
308        | CMPB of {lsrc: operand, rsrc: operand}
309            ``cmpb\t<rsrc>, <lsrc>''
310    
311        | TESTL of {lsrc: operand, rsrc: operand}
312            ``testl\t<rsrc>, <lsrc>''
313    
314        | TESTW of {lsrc: operand, rsrc: operand}
315            ``testw\t<rsrc>, <lsrc>''
316    
317        | TESTB of {lsrc: operand, rsrc: operand}
318            ``testb\t<rsrc>, <lsrc>''
319    
320      | BINARY of {binOp:binaryOp, src:operand, dst:operand}      | BINARY of {binOp:binaryOp, src:operand, dst:operand}
321          ``<binOp>l\t<src>, <dst>''          asm: (case (src,binOp) of
322                   (I.Direct _,
323                   (I.SARL | I.SHRL | I.SHLL |
324                    I.SARW | I.SHRW | I.SHLW |
325                    I.SARB | I.SHRB | I.SHLB)) => ``<binOp>\t%cl, <dst>''
326                 | _ => ``<binOp>\t<src>, <dst>''
327                 )
328    
329      | MULTDIV of {multDivOp:multDivOp, src:operand}      | MULTDIV of {multDivOp:multDivOp, src:operand}
330          ``<multDivOp>l\t<src>''          ``<multDivOp>\t<src>''
331    
332      | MUL3 of {dst:int, src1:operand, src2: Int32.int option}      | MUL3 of {dst: $GP, src2: Int32.int option, src1:operand}
333          ``imul\t<src1>, <emit_src2 src2><dst>''          (* Fermin: constant operand must go first *)
334            asm: (case src2 of
335                    NONE => ``imul\t<src1>, <dst>''
336                  | SOME i => ``imul\t$<emitInt32 i>, <src1>, <dst>''
337                 )
338    
339      | UNARY of {unOp:unaryOp, opnd:operand}      | UNARY of {unOp:unaryOp, opnd:operand}
340          ``<unOp>l\t<opnd>''          ``<unOp>\t<opnd>''
341    
342          (* set byte on condition code; note that
343           * this only sets the low order byte, so it also
344           * uses its operand.
345           *)
346        | SET of {cond:cond, opnd:operand}
347             ``set<cond>\t<opnd>''
348    
349            (* conditional move; Pentium Pro or higher only
350             * Destination must be a register.
351             *)
352        | CMOV of {cond:cond, src:operand, dst: $GP}
353            ``cmov<cond>\t<src>, <dst>''
354    
355      | PUSH of operand      | PUSHL of operand
356          ``pushl\t<operand>''          ``pushl\t<operand>''
357    
358        | PUSHW of operand
359            ``pushw\t<operand>''
360    
361        | PUSHB of operand
362            ``pushb\t<operand>''
363    
364      | POP of operand      | POP of operand
365          ``popl\t<operand>''          ``popl\t<operand>''
366    
# Line 257  Line 372 
372    
373     (* parallel copies *)     (* parallel copies *)
374      | COPY of {dst: $GP list, src: $GP list, tmp:operand option}      | COPY of {dst: $GP list, src: $GP list, tmp:operand option}
375          ``<emitInstrs (Shuffle.shuffle{regmap,tmp,dst,src})>''          asm: emitInstrs (Shuffle.shuffle{regmap,tmp,dst,src})
     | FCOPY of {dst: $FP list, src: $FP list, tmp:operand option}  
         ``<emitInstrs (Shuffle.shufflefp{regmap,tmp,dst,src})>''  
376    
377        | FCOPY of {dst: $FP list, src: $FP list, tmp:operand option}
378            asm: emitInstrs (Shuffle.shufflefp{regmap,tmp,dst,src})
379    
380     (* floating *)     (* floating *)
381      | FBINARY of {binOp:fbinOp, src:operand, dst:operand}      | FBINARY of {binOp:fbinOp, src:operand, dst:operand}
382          ``<binOp>\t<src>, <dst>''          asm: (if isMemOpnd src then ``<binOp>\t<src>''
383                  else ``<emit(chop(asm_fbinOp binOp))>\t<src>, <dst>''
384                 )
385    
386        | FIBINARY of {binOp:fibinOp, src:operand}
387            asm: ``<binOp>\t<src>'' (* the implied destination is %ST(0) *)
388    
389      | FUNARY of funOp      | FUNARY of funOp
390          ``<funOp>''          ``<funOp>''
# Line 272  Line 392 
392      | FUCOMPP      | FUCOMPP
393          ``fucompp''          ``fucompp''
394    
395      | FXCH      | FCOMPP
396          ``fxch''          ``fcompp''
397    
398        | FXCH of {opnd: $FP}
399            asm: (``fxch\t''; if opnd = C.ST(1) then () else ``<opnd>'')
400    
401        | FSTPL of operand
402            ``fstpl\t<operand>''
403    
404      | FSTP of operand      | FSTPS of operand
405          ``fstp\t<operand>''          ``fstps\t<operand>''
406    
407      | FLD of operand      | FSTPT of operand
408          ``fld\t<operand>''          ``fstps\t<operand>''
409    
410        | FSTL of operand
411            ``fstl\t<operand>''
412    
413        | FSTS of operand
414            ``fsts\t<operand>''
415    
416        | FLD1
417            ``fld1''
418    
419        | FLDL2E
420            ``fldl2e''
421    
422        | FLDL2T
423            ``fldl2t''
424    
425        | FLDLG2
426            ``fldlg2''
427    
428        | FLDLN2
429            ``fldln2''
430    
431        | FLDPI
432            ``fldpi''
433    
434        | FLDZ
435            ``fldz''
436    
437        | FLDL of operand
438            ``fldl\t<operand>''
439    
440        | FLDS of operand
441            ``flds\t<operand>''
442    
443        | FLDT of operand
444            ``fldt\t<operand>''
445    
446      | FILD of operand      | FILD of operand
447          ``fild\t<operand>''          ``fild\t<operand>''
448    
449        | FILDL of operand
450            ``fildl\t<operand>''
451    
452        | FILDLL of operand
453            ``fildll\t<operand>''
454    
455      | FNSTSW      | FNSTSW
456          ``fnstsw''          ``fnstsw''
457    
458        | FENV of {fenvOp:fenvOp, opnd:operand} (* load/store environment *)
459            ``<fenvOp>\t<opnd>''
460    
461     (* misc *)     (* misc *)
462      | SAHF      | SAHF
463          ``sahf''          ``sahf''
464    
465     (* annotations *)     (* annotations *)
466      | ANNOTATION of {i:instruction, a:Annotations.annotation}      | ANNOTATION of {i:instruction, a:Annotations.annotation}
467          ``<(emitInstr i; comment(Annotations.toString a))>''          asm: (comment(Annotations.toString a); nl(); emitInstr i)
468    
469      | GROUP of Annotations.annotation      | SOURCE of {}
470          ``<comment(Annotations.toString annotation)>''          asm: ``source''
471            mc:  ()
472    
473        | SINK of {}
474            asm: ``sink''
475            mc:  ()
476    
477        | PHI of {}
478            asm: ``phi''
479            mc:  ()
480    
481  end  end
482    

Legend:
Removed from v.429  
changed lines
  Added in v.624

root@smlnj-gforge.cs.uchicago.edu
ViewVC Help
Powered by ViewVC 1.0.0