mirror of
https://github.com/Z3Prover/z3
synced 2025-04-27 10:55:50 +00:00
Add get_sort(expr * n) function that does not depend on ast_manager. Move power_of_two to rational class. Add arith_recognizers and bv_recognizers classes. The two new classes contain the 'read-only' methods from arith_util and bv_util.
Signed-off-by: Leonardo de Moura <leonardo@microsoft.com>
This commit is contained in:
parent
4f0d5a5756
commit
cec328cfdc
17 changed files with 314 additions and 282 deletions
|
@ -283,12 +283,12 @@ br_status bv_rewriter::mk_leq_core(bool is_signed, expr * a, expr * b, expr_ref
|
|||
|
||||
if (is_num1 || is_num2) {
|
||||
if (is_signed) {
|
||||
lower = - m_util.power_of_two(sz - 1);
|
||||
upper = m_util.power_of_two(sz - 1) - numeral(1);
|
||||
lower = - rational::power_of_two(sz - 1);
|
||||
upper = rational::power_of_two(sz - 1) - numeral(1);
|
||||
}
|
||||
else {
|
||||
lower = numeral(0);
|
||||
upper = m_util.power_of_two(sz) - numeral(1);
|
||||
upper = rational::power_of_two(sz) - numeral(1);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -387,14 +387,14 @@ br_status bv_rewriter::mk_extract(unsigned high, unsigned low, expr * arg, expr_
|
|||
if (is_numeral(arg, v, sz)) {
|
||||
sz = high - low + 1;
|
||||
if (v.is_neg())
|
||||
mod(v, m_util.power_of_two(sz), v);
|
||||
mod(v, rational::power_of_two(sz), v);
|
||||
if (v.is_uint64()) {
|
||||
uint64 u = v.get_uint64();
|
||||
uint64 e = shift_right(u, low) & (shift_left(1ull, sz) - 1ull);
|
||||
result = mk_numeral(numeral(e, numeral::ui64()), sz);
|
||||
return BR_DONE;
|
||||
}
|
||||
div(v, m_util.power_of_two(low), v);
|
||||
div(v, rational::power_of_two(low), v);
|
||||
result = mk_numeral(v, sz);
|
||||
return BR_DONE;
|
||||
}
|
||||
|
@ -519,7 +519,7 @@ br_status bv_rewriter::mk_bv_shl(expr * arg1, expr * arg2, expr_ref & result) {
|
|||
|
||||
SASSERT(r2 < numeral(bv_size));
|
||||
SASSERT(r2.is_unsigned());
|
||||
r1 = m_util.norm(r1 * m_util.power_of_two(r2.get_unsigned()), bv_size);
|
||||
r1 = m_util.norm(r1 * rational::power_of_two(r2.get_unsigned()), bv_size);
|
||||
result = mk_numeral(r1, bv_size);
|
||||
return BR_DONE;
|
||||
}
|
||||
|
@ -567,7 +567,7 @@ br_status bv_rewriter::mk_bv_lshr(expr * arg1, expr * arg2, expr_ref & result) {
|
|||
|
||||
SASSERT(r2.is_unsigned());
|
||||
unsigned sh = r2.get_unsigned();
|
||||
div(r1, m_util.power_of_two(sh), r1);
|
||||
div(r1, rational::power_of_two(sh), r1);
|
||||
result = mk_numeral(r1, bv_size);
|
||||
return BR_DONE;
|
||||
}
|
||||
|
@ -626,7 +626,7 @@ br_status bv_rewriter::mk_bv_ashr(expr * arg1, expr * arg2, expr_ref & result) {
|
|||
|
||||
if (is_num1 && is_num2 && numeral(bv_size) <= r2) {
|
||||
if (m_util.has_sign_bit(r1, bv_size))
|
||||
result = mk_numeral(m_util.power_of_two(bv_size) - numeral(1), bv_size);
|
||||
result = mk_numeral(rational::power_of_two(bv_size) - numeral(1), bv_size);
|
||||
else
|
||||
result = mk_numeral(0, bv_size);
|
||||
return BR_DONE;
|
||||
|
@ -635,7 +635,7 @@ br_status bv_rewriter::mk_bv_ashr(expr * arg1, expr * arg2, expr_ref & result) {
|
|||
if (is_num1 && is_num2) {
|
||||
SASSERT(r2 < numeral(bv_size));
|
||||
bool sign = m_util.has_sign_bit(r1, bv_size);
|
||||
div(r1, m_util.power_of_two(r2.get_unsigned()), r1);
|
||||
div(r1, rational::power_of_two(r2.get_unsigned()), r1);
|
||||
if (sign) {
|
||||
// pad ones.
|
||||
numeral p(1);
|
||||
|
@ -697,7 +697,7 @@ br_status bv_rewriter::mk_bv_sdiv_core(expr * arg1, expr * arg2, bool hi_div0, e
|
|||
// The "hardware interpretation" for (bvsdiv x 0) is (ite (bvslt x #x0000) #x0001 #xffff)
|
||||
result = m().mk_ite(m().mk_app(get_fid(), OP_SLT, arg1, mk_numeral(0, bv_size)),
|
||||
mk_numeral(1, bv_size),
|
||||
mk_numeral(m_util.power_of_two(bv_size) - numeral(1), bv_size));
|
||||
mk_numeral(rational::power_of_two(bv_size) - numeral(1), bv_size));
|
||||
return BR_REWRITE2;
|
||||
}
|
||||
}
|
||||
|
@ -746,7 +746,7 @@ br_status bv_rewriter::mk_bv_udiv_core(expr * arg1, expr * arg2, bool hi_div0, e
|
|||
}
|
||||
else {
|
||||
// The "hardware interpretation" for (bvudiv x 0) is #xffff
|
||||
result = mk_numeral(m_util.power_of_two(bv_size) - numeral(1), bv_size);
|
||||
result = mk_numeral(rational::power_of_two(bv_size) - numeral(1), bv_size);
|
||||
return BR_DONE;
|
||||
|
||||
}
|
||||
|
@ -845,7 +845,7 @@ bool bv_rewriter::is_minus_one_core(expr * arg) const {
|
|||
numeral r;
|
||||
unsigned bv_size;
|
||||
if (is_numeral(arg, r, bv_size)) {
|
||||
return r == (m_util.power_of_two(bv_size) - numeral(1));
|
||||
return r == (rational::power_of_two(bv_size) - numeral(1));
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
@ -924,7 +924,7 @@ br_status bv_rewriter::mk_bv_urem_core(expr * arg1, expr * arg2, bool hi_div0, e
|
|||
if (is_x_minus_one(arg1, x) && x == arg2) {
|
||||
bv_size = get_bv_size(arg1);
|
||||
expr * x_minus_1 = arg1;
|
||||
expr * minus_one = mk_numeral(m_util.power_of_two(bv_size) - numeral(1), bv_size);
|
||||
expr * minus_one = mk_numeral(rational::power_of_two(bv_size) - numeral(1), bv_size);
|
||||
result = m().mk_ite(m().mk_eq(x, mk_numeral(0, bv_size)),
|
||||
m().mk_app(get_fid(), OP_BUREM0, minus_one),
|
||||
x_minus_1);
|
||||
|
@ -1068,7 +1068,7 @@ br_status bv_rewriter::mk_concat(unsigned num_args, expr * const * args, expr_re
|
|||
if (i > 0)
|
||||
prev = new_args.back();
|
||||
if (is_numeral(arg, v1, sz1) && prev != 0 && is_numeral(prev, v2, sz2)) {
|
||||
v2 *= m_util.power_of_two(sz1);
|
||||
v2 *= rational::power_of_two(sz1);
|
||||
v2 += v1;
|
||||
new_args.pop_back();
|
||||
new_args.push_back(mk_numeral(v2, sz1+sz2));
|
||||
|
@ -1137,7 +1137,7 @@ br_status bv_rewriter::mk_sign_extend(unsigned n, expr * arg, expr_ref & result)
|
|||
if (is_numeral(arg, r, bv_size)) {
|
||||
unsigned result_bv_size = bv_size + n;
|
||||
r = m_util.norm(r, bv_size, true);
|
||||
mod(r, m_util.power_of_two(result_bv_size), r);
|
||||
mod(r, rational::power_of_two(result_bv_size), r);
|
||||
result = mk_numeral(r, result_bv_size);
|
||||
return BR_DONE;
|
||||
}
|
||||
|
@ -1213,7 +1213,7 @@ br_status bv_rewriter::mk_bv_or(unsigned num, expr * const * args, expr_ref & re
|
|||
if (m_util.is_bv_not(arg)) {
|
||||
expr * atom = to_app(arg)->get_arg(0);
|
||||
if (pos_args.is_marked(atom)) {
|
||||
result = mk_numeral(m_util.power_of_two(sz) - numeral(1), sz);
|
||||
result = mk_numeral(rational::power_of_two(sz) - numeral(1), sz);
|
||||
return BR_DONE;
|
||||
}
|
||||
else if (neg_args.is_marked(atom)) {
|
||||
|
@ -1229,7 +1229,7 @@ br_status bv_rewriter::mk_bv_or(unsigned num, expr * const * args, expr_ref & re
|
|||
continue;
|
||||
}
|
||||
else if (neg_args.is_marked(arg)) {
|
||||
result = mk_numeral(m_util.power_of_two(sz) - numeral(1), sz);
|
||||
result = mk_numeral(rational::power_of_two(sz) - numeral(1), sz);
|
||||
return BR_DONE;
|
||||
}
|
||||
pos_args.mark(arg, true);
|
||||
|
@ -1237,7 +1237,7 @@ br_status bv_rewriter::mk_bv_or(unsigned num, expr * const * args, expr_ref & re
|
|||
}
|
||||
}
|
||||
|
||||
if (v1 == m_util.power_of_two(sz) - numeral(1)) {
|
||||
if (v1 == rational::power_of_two(sz) - numeral(1)) {
|
||||
result = mk_numeral(v1, sz);
|
||||
return BR_DONE;
|
||||
}
|
||||
|
@ -1294,7 +1294,7 @@ br_status bv_rewriter::mk_bv_or(unsigned num, expr * const * args, expr_ref & re
|
|||
}
|
||||
if (i != low) {
|
||||
unsigned num_sz = i - low;
|
||||
exs.push_back(m_util.mk_numeral(m_util.power_of_two(num_sz) - numeral(1), num_sz));
|
||||
exs.push_back(m_util.mk_numeral(rational::power_of_two(num_sz) - numeral(1), num_sz));
|
||||
low = i;
|
||||
}
|
||||
while (i < sz && mod(v1, two).is_zero()) {
|
||||
|
@ -1385,7 +1385,7 @@ br_status bv_rewriter::mk_bv_xor(unsigned num, expr * const * args, expr_ref & r
|
|||
else if (pos_args.is_marked(atom)) {
|
||||
pos_args.mark(atom, false);
|
||||
merged = true;
|
||||
v1 = bitwise_xor(v1, m_util.power_of_two(sz) - numeral(1));
|
||||
v1 = bitwise_xor(v1, rational::power_of_two(sz) - numeral(1));
|
||||
}
|
||||
else {
|
||||
neg_args.mark(atom, true);
|
||||
|
@ -1399,7 +1399,7 @@ br_status bv_rewriter::mk_bv_xor(unsigned num, expr * const * args, expr_ref & r
|
|||
else if (neg_args.is_marked(arg)) {
|
||||
neg_args.mark(arg, false);
|
||||
merged = true;
|
||||
v1 = bitwise_xor(v1, m_util.power_of_two(sz) - numeral(1));
|
||||
v1 = bitwise_xor(v1, rational::power_of_two(sz) - numeral(1));
|
||||
}
|
||||
else {
|
||||
pos_args.mark(arg, true);
|
||||
|
@ -1455,7 +1455,7 @@ br_status bv_rewriter::mk_bv_xor(unsigned num, expr * const * args, expr_ref & r
|
|||
return BR_REWRITE3;
|
||||
}
|
||||
|
||||
if (!merged && !flattened && (num_coeffs == 0 || (num_coeffs == 1 && !v1.is_zero() && v1 != (m_util.power_of_two(sz) - numeral(1)))))
|
||||
if (!merged && !flattened && (num_coeffs == 0 || (num_coeffs == 1 && !v1.is_zero() && v1 != (rational::power_of_two(sz) - numeral(1)))))
|
||||
return BR_FAILED;
|
||||
|
||||
ptr_buffer<expr> new_args;
|
||||
|
@ -1611,7 +1611,7 @@ br_status bv_rewriter::mk_bv_redand(expr * arg, expr_ref & result) {
|
|||
numeral r;
|
||||
unsigned bv_size;
|
||||
if (is_numeral(arg, r, bv_size)) {
|
||||
result = (r == m_util.power_of_two(bv_size) - numeral(1)) ? mk_numeral(1, 1) : mk_numeral(0, 1);
|
||||
result = (r == rational::power_of_two(bv_size) - numeral(1)) ? mk_numeral(1, 1) : mk_numeral(0, 1);
|
||||
return BR_DONE;
|
||||
}
|
||||
return BR_FAILED;
|
||||
|
@ -1707,7 +1707,7 @@ bool bv_rewriter::is_zero_bit(expr * x, unsigned idx) {
|
|||
if (is_numeral(x, val, bv_size)) {
|
||||
if (val.is_zero())
|
||||
return true;
|
||||
div(val, m_util.power_of_two(idx), val);
|
||||
div(val, rational::power_of_two(idx), val);
|
||||
return (val % numeral(2)).is_zero();
|
||||
}
|
||||
if (m_util.is_concat(x)) {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue