From 53cfa472141fc9dd5c6f07e62a1786243636f846 Mon Sep 17 00:00:00 2001 From: "Christoph M. Wintersteiger" Date: Tue, 25 Nov 2014 14:22:50 +0000 Subject: [PATCH] bugfix for bv_size_reduction Signed-off-by: Christoph M. Wintersteiger --- src/tactic/bv/bv_size_reduction_tactic.cpp | 26 ++++++++++++++++++---- 1 file changed, 22 insertions(+), 4 deletions(-) diff --git a/src/tactic/bv/bv_size_reduction_tactic.cpp b/src/tactic/bv/bv_size_reduction_tactic.cpp index 14a2fb28d..5e32bf6c4 100644 --- a/src/tactic/bv/bv_size_reduction_tactic.cpp +++ b/src/tactic/bv/bv_size_reduction_tactic.cpp @@ -229,17 +229,35 @@ struct bv_size_reduction_tactic::imp { else { // l < u if (l.is_neg()) { - unsigned i_nb = (u - l).get_num_bits() + 1; + unsigned l_nb = (-l).get_num_bits(); unsigned v_nb = m_util.get_bv_size(v); - if (i_nb < v_nb) { - new_const = m.mk_fresh_const(0, m_util.mk_sort(i_nb)); - new_def = m_util.mk_sign_extend(v_nb - i_nb, new_const); + + if (u.is_neg()) + { + // l <= v <= u <= 0 + unsigned i_nb = l_nb; + TRACE("bv_size_reduction", tout << " l <= " << v->get_decl()->get_name() << " <= u <= 0 " << " --> " << i_nb << " bits\n";); + if (i_nb < v_nb) { + new_const = m.mk_fresh_const(0, m_util.mk_sort(i_nb)); + new_def = m_util.mk_concat(m_util.mk_numeral(numeral(-1), v_nb - i_nb), new_const); + } + } + else { + // l <= v <= 0 <= u + unsigned u_nb = u.get_num_bits(); + unsigned i_nb = ((l_nb > u_nb) ? l_nb : u_nb) + 1; + TRACE("bv_size_reduction", tout << " l <= " << v->get_decl()->get_name() << " <= 0 <= u " << " --> " << i_nb << " bits\n";); + if (i_nb < v_nb) { + new_const = m.mk_fresh_const(0, m_util.mk_sort(i_nb)); + new_def = m_util.mk_sign_extend(v_nb - i_nb, new_const); + } } } else { // 0 <= l <= v <= u unsigned u_nb = u.get_num_bits(); unsigned v_nb = m_util.get_bv_size(v); + TRACE("bv_size_reduction", tout << l << " <= " << v->get_decl()->get_name() << " <= " << u << " --> " << u_nb << " bits\n";); if (u_nb < v_nb) { new_const = m.mk_fresh_const(0, m_util.mk_sort(u_nb)); new_def = m_util.mk_concat(m_util.mk_numeral(numeral(0), v_nb - u_nb), new_const);