33 Author: Henny Sipma
44 ------------------------------------------------------------------------------
55 The MIT License (MIT)
6-
6+
77 Copyright (c) 2005-2019 Kestrel Technology LLC
88 Copyright (c) 2020 Henny Sipma
99 Copyright (c) 2021-2022 Aarno Labs LLC
1414 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
1515 copies of the Software, and to permit persons to whom the Software is
1616 furnished to do so, subject to the following conditions:
17-
17+
1818 The above copyright notice and this permission notice shall be included in all
1919 copies or substantial portions of the Software.
20-
20+
2121 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
2222 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
2323 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
@@ -39,74 +39,116 @@ open CHNestedCommands
3939
4040(* xprlib *)
4141open Xprt
42- open XprTypes
42+ open XprTypes
4343open Xsimplify
4444
4545(* ===============================================================================
4646 Conversion of xpr_t to engine expressions + code
47- ===============================================================================
47+ ===============================================================================
4848 *)
49-
49+
5050let xconst_2_numexpr (reqN :tmp_provider_t ) (_reqC :cst_provider_t ) (c :xcst_t ):code_num_t =
5151 match c with
5252 | IntConst num -> (make_nested_nop () , NUM num)
5353 | BoolConst b ->
54- let num = if b then numerical_one else numerical_zero in
54+ let num = if b then numerical_one else numerical_zero in
5555 (make_nested_nop () , NUM num)
5656 | _ -> (make_nested_nop () , NUM_VAR (reqN () ))
5757
58+
5859let xconst_2_boolexpr (_reqN :tmp_provider_t ) (_reqC :cst_provider_t ) (c :xcst_t ):code_bool_t =
5960 let bxpr = match c with
6061 | BoolConst b -> if b then TRUE else FALSE
6162 | IntConst num -> if num#equal numerical_zero then FALSE else TRUE
6263 | _ -> RANDOM in
6364 (make_nested_nop () , bxpr)
6465
66+
6567let rec xpr_2_numexpr (reqN :tmp_provider_t ) (reqC :cst_provider_t ) (xpr :xpr_t ):code_num_t =
6668 match xpr with
6769 XVar v -> (make_nested_nop () , NUM_VAR v)
6870 | XConst c -> xconst_2_numexpr reqN reqC c
6971 | XOp (op , l ) -> xop_2_numexpr reqN reqC op l
7072 | XAttr _ -> (make_nested_nop () , NUM_VAR (reqN () ))
71-
73+
74+
7275and xop_2_numexpr (reqN :tmp_provider_t ) (reqC :cst_provider_t ) (op :xop_t ) (l :xpr_t list ):code_num_t =
7376 match (op,l) with
74- | (_ , [] ) ->
75- raise (CHFailure (LBLOCK [ STR " Empty operand list in xop_2_numexpr" ]))
77+ | (_ , [] ) ->
78+ raise (CHFailure (LBLOCK [STR " Empty operand list in xop_2_numexpr" ]))
7679
7780 | (XNeg, [e ]) ->
78- xpr_2_numexpr reqN reqC (XOp (XMinus , [ zero_constant_expr ; e ]))
81+ xpr_2_numexpr reqN reqC (XOp (XMinus , [zero_constant_expr; e]))
7982
8083 | (XLNot , [_e])
8184 | (XBNot , [_e])
8285 | (XXlsb , [_e])
8386 | (XXlsh, [_e ]) ->
8487 (make_nested_nop () , NUM_VAR (reqN () ))
8588
86- | (XMult , [ XConst (IntConst n) ; XVar v ])
87- | (XMult, [ XVar v ; XConst (IntConst n ) ]) when n#equal (mkNumerical 2 ) ->
89+ | (XMult , [XConst (IntConst n); XVar v])
90+ | (XMult, [XVar v ; XConst (IntConst n )]) when n#equal (mkNumerical 2 ) ->
8891 (make_nested_nop () , PLUS (v, v))
8992
90- | (XMult , [ XConst (IntConst n) ; XVar v ])
91- | (XMult, [ XVar v ; XConst (IntConst n ) ]) when n#equal (mkNumerical 4 ) ->
93+ | (XMult , [XConst (IntConst n); XVar v])
94+ | (XMult, [XVar v ; XConst (IntConst n )]) when n#equal (mkNumerical 4 ) ->
9295 let tmp = reqN () in
9396 let asgn1 = make_nested_cmd (ASSIGN_NUM (tmp, PLUS (v,v))) in
9497 let asgn2 = make_nested_cmd (ASSIGN_NUM (tmp, PLUS (tmp,tmp))) in
95- (make_nested_cmd_block [ asgn1 ; asgn2 ], NUM_VAR tmp)
98+ (make_nested_cmd_block [asgn1; asgn2], NUM_VAR tmp)
9699
97- | (XMult , [ XConst (IntConst n) ; XVar v ])
98- | (XMult, [ XVar v ; XConst (IntConst n ) ]) when n#equal (mkNumerical 8 ) ->
100+ | (XMult , [XConst (IntConst n); XVar v])
101+ | (XMult, [XVar v ; XConst (IntConst n )]) when n#equal (mkNumerical 8 ) ->
99102 let tmp1 = reqN () in
100103 let tmp2 = reqN () in
101104 let asgn1 = make_nested_cmd (ASSIGN_NUM (tmp1, PLUS (v,v))) in
102105 let asgn2 = make_nested_cmd (ASSIGN_NUM (tmp2, PLUS (tmp1,tmp1))) in
103106 let asgn3 = make_nested_cmd (ASSIGN_NUM (tmp2, PLUS (tmp2,tmp2))) in
104- (make_nested_cmd_block [ asgn1 ; asgn2 ; asgn3 ], NUM_VAR tmp2)
105-
106- | (XPlus , [ e1 ; e2 ])
107- | (XMinus , [ e1 ; e2 ])
108- | (XMult , [ e1 ; e2 ])
109- | (XDiv, [ e1 ; e2 ]) ->
107+ (make_nested_cmd_block [asgn1; asgn2; asgn3], NUM_VAR tmp2)
108+
109+ | (XMult , [XConst (IntConst n); XVar v])
110+ | (XMult, [XVar v ; XConst (IntConst n )]) when n#equal (mkNumerical 16 ) ->
111+ let tmp1 = reqN () in
112+ let tmp2 = reqN () in
113+ let tmp3 = reqN () in
114+ let asgn1 = make_nested_cmd (ASSIGN_NUM (tmp1, PLUS (v,v))) in
115+ let asgn2 = make_nested_cmd (ASSIGN_NUM (tmp2, PLUS (tmp1,tmp1))) in
116+ let asgn3 = make_nested_cmd (ASSIGN_NUM (tmp3, PLUS (tmp2,tmp2))) in
117+ let asgn4 = make_nested_cmd (ASSIGN_NUM (tmp3, PLUS (tmp3,tmp3))) in
118+ (make_nested_cmd_block [asgn1; asgn2; asgn3; asgn4], NUM_VAR tmp3)
119+
120+ | (XMult , [XConst (IntConst n); XVar v])
121+ | (XMult, [XVar v ; XConst (IntConst n )]) when n#equal (mkNumerical 16 ) ->
122+ let tmp1 = reqN () in
123+ let tmp2 = reqN () in
124+ let tmp3 = reqN () in
125+ let tmp4 = reqN () in
126+ let asgn1 = make_nested_cmd (ASSIGN_NUM (tmp1, PLUS (v,v))) in
127+ let asgn2 = make_nested_cmd (ASSIGN_NUM (tmp2, PLUS (tmp1,tmp1))) in
128+ let asgn3 = make_nested_cmd (ASSIGN_NUM (tmp3, PLUS (tmp2,tmp2))) in
129+ let asgn4 = make_nested_cmd (ASSIGN_NUM (tmp3, PLUS (tmp3,tmp3))) in
130+ let asgn5 = make_nested_cmd (ASSIGN_NUM (tmp3, PLUS (tmp4,tmp4))) in
131+ (make_nested_cmd_block [asgn1; asgn2; asgn3; asgn4; asgn5], NUM_VAR tmp4)
132+
133+ | (XMult , [XConst (IntConst n); XVar v])
134+ | (XMult, [XVar v ; XConst (IntConst n )]) when n#equal (mkNumerical 32 ) ->
135+ let tmp1 = reqN () in
136+ let tmp2 = reqN () in
137+ let tmp3 = reqN () in
138+ let tmp4 = reqN () in
139+ let tmp5 = reqN () in
140+ let asgn1 = make_nested_cmd (ASSIGN_NUM (tmp1, PLUS (v,v))) in
141+ let asgn2 = make_nested_cmd (ASSIGN_NUM (tmp2, PLUS (tmp1,tmp1))) in
142+ let asgn3 = make_nested_cmd (ASSIGN_NUM (tmp3, PLUS (tmp2,tmp2))) in
143+ let asgn4 = make_nested_cmd (ASSIGN_NUM (tmp3, PLUS (tmp3,tmp3))) in
144+ let asgn5 = make_nested_cmd (ASSIGN_NUM (tmp3, PLUS (tmp4,tmp4))) in
145+ let asgn6 = make_nested_cmd (ASSIGN_NUM (tmp3, PLUS (tmp5,tmp5))) in
146+ (make_nested_cmd_block [asgn1; asgn2; asgn3; asgn4; asgn5; asgn6], NUM_VAR tmp5)
147+
148+ | (XPlus , [e1; e2])
149+ | (XMinus , [e1; e2])
150+ | (XMult , [e1; e2])
151+ | (XDiv, [e1 ; e2 ]) ->
110152 let (c1,r1) = xpr_2_numvar reqN reqC e1 in
111153 let (c2,r2) = xpr_2_numvar reqN reqC e2 in
112154 let num_expr =
@@ -117,72 +159,76 @@ and xop_2_numexpr (reqN:tmp_provider_t) (reqC:cst_provider_t) (op:xop_t) (l:xpr_
117159 | XDiv -> DIV (r1, r2)
118160 | _ ->
119161 failwith " Unexpected operator in xop_2_numexpr" in
120- (make_nested_cmd_block [ c1 ; c2 ], num_expr)
162+ (make_nested_cmd_block [c1 ; c2], num_expr)
121163
122- | (XMod, [ XConst (IntConst n1 ) ; XConst (IntConst n2 ) ]) ->
164+ | (XMod, [XConst (IntConst n1 ); XConst (IntConst n2 )]) ->
123165 (make_nested_nop () , NUM (n1#modulo n2))
124166
125- | (XNumRange, [e1 ; e2 ]) ->
167+ | (XNumRange, [e1 ; e2 ]) ->
126168 let tmp = reqN () in
127- let lb = XOp (XGe , [ XVar tmp ; e1 ]) in
128- let ub = XOp (XLe , [ XVar tmp ; e2 ]) in
169+ let lb = XOp (XGe , [XVar tmp; e1]) in
170+ let ub = XOp (XLe , [XVar tmp; e2]) in
129171 let (lbc,lbe) = xpr_2_boolexpr reqN reqC lb in
130172 let (ubc,ube) = xpr_2_boolexpr reqN reqC ub in
131173 let lba = make_nested_cmd (ASSERT lbe) in
132174 let uba = make_nested_cmd (ASSERT ube) in
133- let code = make_nested_cmd_block [ lbc ; ubc ; lba ; uba ] in
175+ let code = make_nested_cmd_block [lbc; ubc; lba; uba] in
134176 (code, NUM_VAR tmp)
135177
136178 | _ ->
137179 (make_nested_nop () , NUM_VAR (reqN () ))
138180
181+
139182and xpr_2_numvar (reqN :tmp_provider_t ) (reqC :cst_provider_t ) (xpr :xpr_t ):code_var_t =
140183 match xpr with
141184 | XVar v ->
142185 (make_nested_nop () , v)
143- | XConst (IntConst n ) ->
186+ | XConst (IntConst n ) ->
144187 let v = reqC n in (make_nested_nop () , v)
145188 | _ ->
146189 let (c,r) = xpr_2_numexpr reqN reqC xpr in
147190 let tmp = reqN () in
148191 let asgn = make_nested_cmd (ASSIGN_NUM (tmp, r)) in
149- let code = make_nested_cmd_block [ c ; asgn ] in
192+ let code = make_nested_cmd_block [c ; asgn] in
150193 (code, tmp)
151194
195+
152196and xpr_2_boolexpr (reqN :tmp_provider_t ) (reqC :cst_provider_t ) (xpr :xpr_t ):code_bool_t =
153197 match xpr with
154198 | XVar v -> xvar_2_boolexpr reqN reqC v
155199 | XConst c -> xconst_2_boolexpr reqN reqC c
156200 | XOp (op , l ) -> xop_2_boolexpr reqN reqC op l
157201 | _ ->
158- raise (CHFailure (LBLOCK [ STR " Unexpected expression in expr_2_boolexpr" ]))
202+ raise (CHFailure (LBLOCK [STR " Unexpected expression in expr_2_boolexpr" ]))
203+
159204
160205and xvar_2_boolexpr (reqN :tmp_provider_t ) (reqC :cst_provider_t ) (v :variable_t ):code_bool_t =
161206 let bxpr =
162207 if v#isNumerical then
163- XOp (XNe , [XVar v ; zero_constant_expr ])
208+ XOp (XNe , [XVar v; zero_constant_expr])
164209 else
165210 XConst XRandom in
166211 xpr_2_boolexpr reqN reqC bxpr
167212
213+
168214and xop_2_boolexpr (reqN :tmp_provider_t ) (reqC :cst_provider_t ) (op :xop_t ) (l :xpr_t list ) =
169215 let default = (make_nested_nop () , RANDOM ) in
170216 match (op, l) with
171217 (_ , [] ) ->
172218 raise (CHFailure (STR " Empty operand list in xop_2_boolexpr" ))
173219
174220 | (XNeg, [_e ]) ->
175- xpr_2_boolexpr reqN reqC (XOp (XNe , [ XOp (op, l) ; zero_constant_expr]))
221+ xpr_2_boolexpr reqN reqC (XOp (XNe , [XOp (op, l); zero_constant_expr]))
176222 | (XLNot , [_e])
177223 | (XBNot , [_e])
178224 | (XXlsb , [_e])
179225 | (XXlsh, [_e ]) ->
180226 default
181227
182- | (XDisjoint, [XVar v ; XConst (SymSet l ) ]) ->
228+ | (XDisjoint, [XVar v ; XConst (SymSet l )]) ->
183229 (make_nested_nop () , DISJOINT (v,l))
184230
185- | (XSubset, [ XVar v ; XConst (SymSet l ) ]) ->
231+ | (XSubset, [XVar v ; XConst (SymSet l )]) ->
186232 (make_nested_nop () , SUBSET (v, l))
187233
188234 | (XPlus , _)
@@ -218,36 +264,41 @@ and xop_2_boolexpr (reqN:tmp_provider_t) (reqC:cst_provider_t) (op:xop_t) (l:xpr
218264 in
219265 (make_nested_cmd_block [c1; c2], bxpr)
220266
221- | _ ->
267+ | _ ->
222268 default
223269
224270
225271let xpr2numexpr (reqN :tmp_provider_t ) (reqC :cst_provider_t ) (xpr :xpr_t ):code_num_t =
226272 let (_, sim_expr) = simplify_expr xpr in
227273 xpr_2_numexpr reqN reqC sim_expr
228274
275+
229276let xpr2numvar (reqN :tmp_provider_t ) (reqC :cst_provider_t ) (xpr :xpr_t ):code_var_t =
230277 let (_, sim_expr) = simplify_expr xpr in
231278 xpr_2_numvar reqN reqC sim_expr
232279
280+
233281let xpr2boolexpr (reqN :tmp_provider_t ) (reqC :cst_provider_t ) (xpr :xpr_t ):code_bool_t =
234282 let (_, sim_expr) = simplify_expr xpr in
235283 xpr_2_boolexpr reqN reqC sim_expr
236284
285+
237286let xpr_to_numexpr
238287 (reqN :tmp_provider_t )
239288 (reqC :cst_provider_t )
240289 (xpr :xpr_t ):(cmd_t list * numerical_exp_t) =
241290 let (c,e) = xpr2numexpr reqN reqC xpr in
242291 (nested_cmd_2_cmds c, e)
243292
293+
244294let xpr_to_numvar
245295 (reqN :tmp_provider_t )
246296 (reqC :cst_provider_t )
247297 (xpr :xpr_t ):(cmd_t list * variable_t) =
248298 let (c,v) = xpr2numvar reqN reqC xpr in
249299 (nested_cmd_2_cmds c, v)
250300
301+
251302let xpr_to_boolexpr
252303 (reqN :tmp_provider_t )
253304 (reqC :cst_provider_t )
@@ -284,41 +335,50 @@ let occurs_check (var:variable_t) (x:xpr_t) =
284335 | _ -> false in
285336 aux x
286337
338+
287339(* PEPR Conversion *)
288340
289341let pepr_parameter_expr_to_xpr
290342 (params :pepr_params_int )
291343 (coeffs :coeff_vector_int )
292344 (n :numerical_t ) =
293345 let factors = coeffs#get_pairs in
294- simplify_xpr (List. fold_left (fun acc (i ,c ) ->
295- let v = (params#nth i)#get_variable in
296- XOp (XPlus , [ XOp (XMult , [ XVar v ; num_constant_expr c ]) ; acc ]))
297- (num_constant_expr n) factors)
346+ simplify_xpr
347+ (List. fold_left (fun acc (i ,c ) ->
348+ let v = (params#nth i)#get_variable in
349+ XOp (XPlus , [XOp (XMult , [XVar v; num_constant_expr c]); acc]))
350+ (num_constant_expr n) factors)
351+
298352
299353let pex_to_xpr (params :pepr_params_int ) (x :pex_int ) =
300354 if x#is_number then
301355 num_constant_expr x#get_number
302356 else
303- pepr_parameter_expr_to_xpr params x#get_k x#get_n
357+ pepr_parameter_expr_to_xpr params x#get_k x#get_n
358+
304359
305360let pex_set_to_xpr_list (params :pepr_params_int ) (s :pex_set_int ):xpr_t list =
306361 List. map (pex_to_xpr params) s#get_s
307362
363+
308364let pex_pset_to_xpr_list_list (params :pepr_params_int ) (p :pex_pset_int ):xpr_t list list =
309365 List. map (pex_set_to_xpr_list params) p#get_p
310366
367+
311368(* disjunction of conjunction *)
312- let pepr_bound_to_xpr_list_list (params :pepr_params_int ) (b :pepr_bounds_t ):xpr_t list list =
369+ let pepr_bound_to_xpr_list_list
370+ (params :pepr_params_int ) (b :pepr_bounds_t ):xpr_t list list =
313371 match b with
314- | XTOP -> [ [ random_constant_expr ] ]
372+ | XTOP -> [[ random_constant_expr] ]
315373 | XPSET x -> pex_pset_to_xpr_list_list params x
316-
317- let get_pepr_range_xprs (params :pepr_params_int ) (range :pepr_range_int ):pepr_xpr_extract =
374+
375+
376+ let get_pepr_range_xprs
377+ (params :pepr_params_int ) (range :pepr_range_int ):pepr_xpr_extract =
318378 let result = {
319- pepr_n = None ;
320- pepr_i = None ;
321- pepr_equalities = [] ;
379+ pepr_n = None ;
380+ pepr_i = None ;
381+ pepr_equalities = [] ;
322382 pepr_bounds = []
323383 } in
324384 let (range,result) =
@@ -332,26 +392,30 @@ let get_pepr_range_xprs (params:pepr_params_int) (range:pepr_range_int):pepr_xpr
332392 let (range,result) =
333393 List. fold_left (fun (ran ,_res ) (k ,n ) ->
334394 (ran#remove_equality k n,
335- { result with pepr_equalities =
336- (pepr_parameter_expr_to_xpr params k n) :: result.pepr_equalities} ))
337- (range, result) range#parameter_exprs in
395+ { result with
396+ pepr_equalities =
397+ (pepr_parameter_expr_to_xpr params k n) :: result.pepr_equalities} ))
398+ (range, result) range#parameter_exprs in
338399 let result =
339400 match range#get_min#get_bound with
340401 | XTOP -> result
341402 | b -> { result with
342- pepr_bounds = (LB ,pepr_bound_to_xpr_list_list params b) :: result.pepr_bounds } in
403+ pepr_bounds =
404+ (LB ,pepr_bound_to_xpr_list_list params b) :: result.pepr_bounds } in
343405 match range#get_max#get_bound with
344406 | XTOP -> result
345407 | b -> { result with
346408 pepr_bounds = (UB ,pepr_bound_to_xpr_list_list params b) :: result.pepr_bounds }
347409
348- let get_pepr_dependency_xprs (params :pepr_params_int ) (s :param_constraint_set_int ):xpr_t list =
410+
411+ let get_pepr_dependency_xprs
412+ (params :pepr_params_int ) (s :param_constraint_set_int ):xpr_t list =
349413 List. map (fun x ->
350414 let factors = x#get_k#get_pairs in
351415 let xpr =
352- simplify_xpr ( List. fold_left ( fun acc ( i , c ) ->
353- let v = (params#nth i)#get_variable in
354- XOp ( XPlus , [ XOp ( XMult , [ XVar v ; num_constant_expr c ]) ; acc ]))
355- ( num_constant_expr x#get_n) factors) in
356- XOp ( XGe , [ xpr ; zero_constant_expr ])) s#get_s
357-
416+ simplify_xpr
417+ ( List. fold_left ( fun acc ( i , c ) ->
418+ let v = (params#nth i)#get_variable in
419+ XOp ( XPlus , [ XOp ( XMult , [ XVar v; num_constant_expr c]); acc]))
420+ (num_constant_expr x#get_n) factors) in
421+ XOp ( XGe , [xpr; zero_constant_expr])) s#get_s
0 commit comments