ocaml/asmcomp/mach.ml

107 lines
2.6 KiB
OCaml

(* Representation of machine code by sequences of pseudoinstructions *)
type integer_comparison =
Isigned of Cmm.comparison
| Iunsigned of Cmm.comparison
type integer_operation =
Iadd | Isub | Imul | Idiv | Imod
| Iand | Ior | Ixor | Ilsl | Ilsr | Iasr
| Icomp of integer_comparison
type test =
Itruetest
| Ifalsetest
| Iinttest of integer_comparison
| Iinttest_imm of integer_comparison * int
| Ifloattest of Cmm.comparison
type operation =
Imove
| Ispill
| Ireload
| Iconstant of Cmm.constant
| Icall_ind
| Icall_imm of string
| Itailcall_ind
| Itailcall_imm of string
| Iextcall of string
| Istackoffset of int
| Iload of Cmm.memory_chunk * Arch.addressing_mode
| Istore of Cmm.memory_chunk * Arch.addressing_mode
| Ialloc of int
| Imodify
| Iintop of integer_operation
| Iintop_imm of integer_operation * int
| Iaddf | Isubf | Imulf | Idivf
| Ifloatofint | Iintoffloat
| Ispecific of Arch.specific_operation
type instruction =
{ desc: instruction_desc;
next: instruction;
arg: Reg.t array;
res: Reg.t array;
mutable live: Reg.Set.t }
and instruction_desc =
Iend
| Iop of operation
| Ireturn
| Iifthenelse of test * instruction * instruction
| Iswitch of int array * instruction array
| Iloop of instruction
| Icatch of instruction * instruction
| Iexit
| Itrywith of instruction * instruction
| Iraise
type fundecl =
{ fun_name: string;
fun_args: Reg.t array;
fun_body: instruction }
let rec dummy_instr =
{ desc = Iend;
next = dummy_instr;
arg = [||];
res = [||];
live = Reg.Set.empty }
let end_instr () =
{ desc = Iend;
next = dummy_instr;
arg = [||];
res = [||];
live = Reg.Set.empty }
let instr_cons d a r n =
{ desc = d; next = n; arg = a; res = r; live = Reg.Set.empty }
let rec instr_iter f i =
match i.desc with
Iend -> ()
| _ ->
f i;
match i.desc with
Iend -> ()
| Ireturn | Iop(Itailcall_ind) | Iop(Itailcall_imm _) -> ()
| Iifthenelse(tst, ifso, ifnot) ->
instr_iter f ifso; instr_iter f ifnot; instr_iter f i.next
| Iswitch(index, cases) ->
for i = 0 to Array.length cases - 1 do
instr_iter f cases.(i)
done;
instr_iter f i.next
| Iloop(body) ->
instr_iter f body; instr_iter f i.next
| Icatch(body, handler) ->
instr_iter f body; instr_iter f handler; instr_iter f i.next
| Iexit -> ()
| Itrywith(body, handler) ->
instr_iter f body; instr_iter f handler; instr_iter f i.next
| Iraise -> ()
| _ ->
instr_iter f i.next