2 (** This module defines parameterized arithmetic expressions, i.e. arithmetic
3 expressions mixed with any other type. For instance, one can define
4 arithmetic expressions with function calls, arithmetic expressions with top
5 and bottom (the abstract interpretation constants), etc. *)
7 (* Note: the feature 'mixed with any other type' is not used anymore. It would
8 make the code clearer to remove it. *)
13 type relation = Lt | Gt | Le | Ge
15 let is_large = function
19 let has_lower_type = function
23 let string_of_relation = function
29 let mk_strict = function
33 let mk_large = function
37 let opposite = function
45 type binop = Add | Sub | Div | Mul | Mod | Max
47 let string_of_unop = function
50 let string_of_binop = function
62 | UnOp of unop * 'a tt
63 | BinOp of binop * 'a tt * 'a tt
64 | Cond of 'a tt * relation * 'a tt * 'a tt * 'a tt (* ternary expressions *)
66 let compare compare_a v1 v2 = match v1, v2 with
67 | A a1, A a2 -> compare_a a1 a2
70 | _ -> Pervasives.compare v1 v2
72 let rec map f = function
76 | UnOp (unop, v) -> UnOp (unop, map f v)
77 | BinOp (binop, v1, v2) -> BinOp (binop, map f v1, map f v2)
78 | Cond (v1, rel, v2, v3, v4) ->
79 Cond (map f v1, rel, map f v2, map f v3, map f v4)
81 let fill_subs v subs = match v, subs with
82 | A _, _ | Int _, _ | Var _, _ -> v
83 | UnOp (unop, _), v :: _ -> UnOp (unop, v)
84 | BinOp (binop, _, _), v1 :: v2 :: _ -> BinOp (binop, v1, v2)
85 | Cond (_, rel, _, _, _), t1 :: t2 :: tif :: telse :: _ ->
86 Cond (t1, rel, t2, tif, telse)
87 | _ -> raise (Failure "ArithSig.fill_subs") (* wrong number of arguments *)
90 | A _ | Int _ | Var _ -> []
92 | BinOp (_, v1, v2) -> [v1 ; v2]
93 | Cond (t1, _, t2, tif, telse) -> [t1 ; t2 ; tif ; telse]
96 let subs_res = List.map (fold f) (subs v) in
99 let f_is_independent v subs_res =
100 let b = match v with A _ -> false | _ -> true in
101 List.fold_left (&&) true (b :: subs_res)
103 (** [is_independent v] returns true if and only if the arithmetic expression
104 [v] does not mention a value of its parameter type. *)
106 let is_independent v = fold f_is_independent v
108 let f_replace replacements v subs_res =
110 | Var x when List.mem_assoc x replacements -> List.assoc x replacements
114 let replace replacements v = fold (f_replace replacements) v
124 val to_string : t -> string
125 val to_cil_term : t -> Cil_types.term
129 val addl : t -> t tt -> t tt
130 val addr : t tt -> t -> t tt
131 val minusl : t -> t tt -> t tt
132 val minusr : t tt -> t -> t tt
133 val mull : t -> t tt -> t tt
134 val mulr : t tt -> t -> t tt
135 val divl : t -> t tt -> t tt
136 val divr : t tt -> t -> t tt
137 val modl : t -> t tt -> t tt
138 val modr : t tt -> t -> t tt
139 val maxl : t -> t tt -> t tt
140 val maxr : t tt -> t -> t tt
141 val lel : t -> t tt -> bool
142 val ler : t tt -> t -> bool
143 val ltl : t -> t tt -> bool
144 val ltr : t tt -> t -> bool
145 val gel : t -> t tt -> bool
146 val ger : t tt -> t -> bool
147 val gtl : t -> t tt -> bool
148 val gtr : t tt -> t -> bool
150 val compare : t -> t -> int