diff options
Diffstat (limited to 'camlsim/machine.ml')
-rw-r--r-- | camlsim/machine.ml | 174 |
1 files changed, 0 insertions, 174 deletions
diff --git a/camlsim/machine.ml b/camlsim/machine.ml deleted file mode 100644 index 232cb08..0000000 --- a/camlsim/machine.ml +++ /dev/null @@ -1,174 +0,0 @@ -(* - Système Digital, cours de J.Vuillemin, 2013-2013 - Alex AUVOLAT, ENS INFO 2013 - - Circuit Simulator, machine simulator - - ASSUMPTIONS: - - Only one ROM chip -*) - -open Netlist_ast - -exception Error of string -exception Is_not_modified - -let load_rom filename = - () (* TODO *) - - -type ram_prop = int * int (* addr size ; word size *) -type machine = { - p : program; - mutable vars : value Env.t; - mutable regs : value Env.t; - ram_chips : ram_prop array; - ram : value array array; -} - -let rec two_to_the = function - | 0 -> 1 - | n -> let k = (two_to_the (n/2)) in - if n mod 2 = 1 then 2 * k else k - -let create p = - let ram_chips = Array.of_list - (List.fold_left - (fun x (_, v) -> match v with - | Eram (a, w, _, _, _, _) -> - (a, w)::x - | _ -> x) - [] - p.p_eqs) in - let vars = Env.fold - (fun k v x -> - Env.add k - (match v with - | TBit -> VBit(false) - | TBitArray(n) -> VBitArray(Array.make n false)) - x) - p.p_vars - Env.empty in - { - p = p; - vars = vars; - regs = Env.empty; (* no use putting anything at the moment *) - ram_chips = ram_chips; - ram = Array.map - (fun (a, w) -> Array.make (two_to_the a) (VBitArray (Array.make w false))) - ram_chips; - } - -let read_inputs m f = - List.iter - (fun n -> - m.vars <- Env.add n (f (n, Env.find n m.p.p_vars)) m.vars) - m.p.p_inputs - -let step m = - let get = function - | Avar(x) -> - begin match Env.find x m.vars with - | VBit(x) -> VBit(x) - | VBitArray(u) as s -> - if Array.length u = 1 then VBit(u.(0)) else s - end - | Aconst(x) -> x - in - (* Load register values into dest variables *) - Env.iter - (fun k v -> - m.vars <- Env.add k v m.vars) - m.regs; - (* Do all the logic *) - List.iter - (fun (varname, exp) -> - let evaluate = function - | Earg(k) -> get k - | Ereg(_) -> raise Is_not_modified (* do nothing, registers are handled somewhere else *) - | Enot(k) -> - begin match get k with - | VBit(u) -> VBit (not u) - | VBitArray(u) -> VBitArray(Array.map (fun x -> not x) u) - end - | Ebinop(op, k1, k2) -> - let f = begin match op with - | Or -> (fun x y -> x || y) - | Xor -> (fun x y -> (x || y) && (not (x && y))) - | And -> (fun x y -> x && y) - | Nand -> (fun x y -> not (x && y)) - end in - begin match get k1, get k2 with - | VBit(u), VBit(v) -> VBit(f u v) - | VBitArray(u), VBitArray(v) when Array.length u = Array.length v -> - let r = Array.make (Array.length u) false in - for i = 0 to Array.length u - 1 do - r.(i) <- (f u.(i) v.(i)) - done; VBitArray(r) - | VBit(u), VBitArray(v) -> VBit(f u v.(0)) - | VBitArray(u), VBit(v) -> VBit(f u.(0) v) - | _ -> raise (Error "Incompatible data types.") - end - | Emux (control, in0, in1) -> - begin match get control, get in0, get in1 with - | VBit(u), x, y -> - if u then y else x - | VBitArray(u), VBitArray(a), VBitArray(b) - when Array.length a = Array.length b - && Array.length u = Array.length a -> - let r = Array.make (Array.length u) false in - for i = 0 to Array.length u - 1 do - r.(i) <- (if u.(i) then b.(i) else a.(i)) - done; - VBitArray(r) - | _ -> raise (Error "Invalid data size in mux") - end - | Erom(_, w, _) -> VBitArray(Array.make w false) (* TODO *) - | Eram(_, _, _,_, _, _) -> raise Is_not_modified (* TODO *) - | Econcat(k1, k2) -> - let a1 = match get k1 with - | VBit(u) -> [|u|] - | VBitArray(u) -> u - in - let a2 = match get k2 with - | VBit(u) -> [|u|] - | VBitArray(u) -> u - in - VBitArray(Array.append a1 a2) - | Eslice (first, last, k) -> - begin match get k with - | VBit(u) when first = 0 && last = 0 -> VBit(u) - | VBitArray(u) -> - let r = Array.make (last - first) false in - for i = first to last - 1 do - r.(i - first) <- u.(i) - done; - VBitArray(u) - | _ -> raise (Error "Invalid slicing parameters") - end - | Eselect(id, k) -> - begin match get k with - | VBit(u) when id = 0 -> VBit(u) - | VBitArray(u) -> VBit(u.(id)) - | _ -> raise (Error "Invalid select parameters") - end - in - try - m.vars <- Env.add varname (evaluate exp) m.vars - with Is_not_modified -> ()) - m.p.p_eqs; - (* Saves register values *) - m.regs <- List.fold_left - (fun x (k, v) -> - match v with - | Ereg(n) -> Env.add k (Env.find n m.vars) x - | _ -> x) - Env.empty - m.p.p_eqs - -let print_outputs m f = - List.iter - (fun n -> - f (n, Env.find n m.vars)) - m.p.p_outputs - |