@@ -1557,17 +1557,20 @@ br_status seq_rewriter::mk_seq_index(expr* a, expr* b, expr* c, expr_ref& result
15571557 }
15581558
15591559 if (str ().is_empty (b)) {
1560- result = m ().mk_ite (m ().mk_and (m_autil.mk_le (zero (), c),
1561- m_autil.mk_le (c, str ().mk_length (a))),
1562- c,
1563- minus_one ());
1560+ // enforce deterministic evaluation order for bounds checks
1561+ auto a1 = m_autil.mk_le (zero (), c);
1562+ auto b1 = m_autil.mk_le (c, str ().mk_length (a));
1563+ auto cond = m ().mk_and (a1, b1);
1564+ result = m ().mk_ite (cond, c, minus_one ());
15641565 return BR_REWRITE2;
15651566 }
15661567
15671568
15681569 if (str ().is_empty (a)) {
15691570 expr* emp = str ().mk_is_empty (b);
1570- result = m ().mk_ite (m ().mk_and (m ().mk_eq (c, zero ()), emp), zero (), minus_one ());
1571+ auto a1 = m ().mk_eq (c, zero ());
1572+ auto cond = m ().mk_and (a1, emp);
1573+ result = m ().mk_ite (cond, zero (), minus_one ());
15711574 return BR_REWRITE2;
15721575 }
15731576
@@ -2732,11 +2735,15 @@ br_status seq_rewriter::mk_re_reverse(expr* r, expr_ref& result) {
27322735 return BR_REWRITE2;
27332736 }
27342737 else if (re ().is_intersection (r, r1, r2)) {
2735- result = re ().mk_inter (re ().mk_reverse (r1), re ().mk_reverse (r2));
2738+ auto a = re ().mk_reverse (r1);
2739+ auto b = re ().mk_reverse (r2);
2740+ result = re ().mk_inter (a, b);
27362741 return BR_REWRITE2;
27372742 }
27382743 else if (re ().is_diff (r, r1, r2)) {
2739- result = re ().mk_diff (re ().mk_reverse (r1), re ().mk_reverse (r2));
2744+ auto a = re ().mk_reverse (r1);
2745+ auto b = re ().mk_reverse (r2);
2746+ result = re ().mk_diff (a, b);
27402747 return BR_REWRITE2;
27412748 }
27422749 else if (m ().is_ite (r, p, r1, r2)) {
@@ -3031,7 +3038,11 @@ void seq_rewriter::mk_antimirov_deriv_rec(expr* e, expr* r, expr* path, expr_ref
30313038 // SASSERT(u().is_char(c1));
30323039 // SASSERT(u().is_char(c2));
30333040 // case: c1 <= e <= c2
3034- range = simplify_path (e, m ().mk_and (u ().mk_le (c1, e), u ().mk_le (e, c2)));
3041+ // deterministic evaluation for range bounds
3042+ auto a_le = u ().mk_le (c1, e);
3043+ auto b_le = u ().mk_le (e, c2);
3044+ auto rng_cond = m ().mk_and (a_le, b_le);
3045+ range = simplify_path (e, rng_cond);
30353046 psi = simplify_path (e, m ().mk_and (path, range));
30363047 }
30373048 else if (!str ().is_string (r1) && str ().is_unit_string (r2, c2)) {
@@ -4005,8 +4016,13 @@ expr_ref seq_rewriter::mk_derivative_rec(expr* ele, expr* r) {
40054016 // if ((isdigit ele) and (ele = (hd r1))) then (to_re (tl r1)) else []
40064017 //
40074018 hd = mk_seq_first (r1);
4008- m_br.mk_and (u ().mk_le (m_util.mk_char (' 0' ), ele), u ().mk_le (ele, m_util.mk_char (' 9' )),
4009- m ().mk_and (m ().mk_not (m ().mk_eq (r1, str ().mk_empty (seq_sort))), m ().mk_eq (hd, ele)), result);
4019+ // isolate nested conjunction for deterministic evaluation
4020+ auto a0 = u ().mk_le (m_util.mk_char (' 0' ), ele);
4021+ auto a1 = u ().mk_le (ele, m_util.mk_char (' 9' ));
4022+ auto a2 = m ().mk_not (m ().mk_eq (r1, str ().mk_empty (seq_sort)));
4023+ auto a3 = m ().mk_eq (hd, ele);
4024+ auto inner = m ().mk_and (a2, a3);
4025+ m_br.mk_and (a0, a1, inner, result);
40104026 tl = re ().mk_to_re (mk_seq_rest (r1));
40114027 return re_and (result, tl);
40124028 }
@@ -5040,7 +5056,9 @@ void seq_rewriter::elim_condition(expr* elem, expr_ref& cond) {
50405056 rep.insert (elem, solution);
50415057 rep (cond);
50425058 if (!is_uninterp_const (elem)) {
5043- cond = m ().mk_and (m ().mk_eq (elem, solution), cond);
5059+ // ensure deterministic evaluation order when augmenting condition
5060+ auto eq_sol = m ().mk_eq (elem, solution);
5061+ cond = m ().mk_and (eq_sol, cond);
50445062 }
50455063 }
50465064 else if (all_ranges) {
0 commit comments