-
Notifications
You must be signed in to change notification settings - Fork 460
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat: add SMT-LIB overflow on addition for bitvectors BitVec.(uadd_overflow, sadd_overflow, uadd_overflow_eq, sadd_overflow_eq)
and support theorems
#6628
Conversation
Mathlib CI status (docs):
|
changelog-library |
What are your plans for adding theorems about these? |
Ideally supporting them in bvdecide - although there are some proofs missing (they're taking me more time than I expected), so I'll draft the PR for now and open it when the proofs are done! |
Okay! I'm happy with these definitions, and checked them against the reference, so I'm happy to click merge as soon as we're sure they are going to be used. |
not_overflow
,uadd_overflow
,sadd_overflow
,umul_overflow
,smul_overflow
)uadd_overflow
,sadd_overflow
, uadd_overflow_eq
,sadd_overflow_eq
)
Co-authored-by: Tobias Grosser <[email protected]>
Co-authored-by: Tobias Grosser <[email protected]>
Co-authored-by: Alex Keizer <[email protected]>
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Some suggestions for more explicit docstring; feel to free to adapt/ignore
Co-authored-by: Alex Keizer <[email protected]>
Co-authored-by: Alex Keizer <[email protected]>
Co-authored-by: Alex Keizer <[email protected]>
src/Init/Data/BitVec/Bitblast.lean
Outdated
have bmod_neg_iff {m : Nat} {x : Int} (h2 : -m ≤ x) (h1 : x < m) : | ||
(x.bmod m) < 0 ↔ (-(m / 2) ≤ x ∧ x < 0) ∨ ((m + 1) / 2 ≤ x) := by | ||
simp only [Int.bmod_def] | ||
by_cases xpos : 0 ≤ x | ||
· rw [Int.emod_eq_of_lt xpos (by omega)]; omega | ||
· rw [Int.add_emod_self.symm, Int.emod_eq_of_lt (by omega) (by omega)]; omega | ||
simp only [← decide_or, msb_eq_toInt, decide_beq_decide, toInt_add, ← decide_not, ← decide_and, | ||
decide_eq_decide] | ||
rw [bmod_neg_iff (by rw [← Nat.two_pow_pred_add_two_pow_pred (by omega)]; push_cast; omega) | ||
(by rw [← Nat.two_pow_pred_add_two_pow_pred (by omega)]; push_cast; omega), | ||
← @Nat.two_pow_pred_add_two_pow_pred (w + 1) (by omega), Nat.add_one_sub_one] at * |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I wish I could extract out a nice lemma out of this, but I'm sadly not sure what it should be. I suggest we get some more experience proving these theorems, and then consider a refactor of this part of the proof.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM, but I wonder if @kim-em has a cleaner proof strategy for saddOverflow_eq
. I'd be happy to clean up the proof in a later PR, once we have a bit more experience with these kinds of overflow proofs, so we can design a nice API.
awaiting-author |
lgtm! |
This reverts commit 00784d7.
src/Init/Data/BitVec/Bitblast.lean
Outdated
have bmod_neg_iff {m : Nat} {x : Int} (h2 : -m ≤ x) (h1 : x < m) : | ||
(x.bmod m) < 0 ↔ (-(m / 2) ≤ x ∧ x < 0) ∨ ((m + 1) / 2 ≤ x) := by | ||
simp only [Int.bmod_def] | ||
by_cases xpos : 0 ≤ x | ||
· rw [Int.emod_eq_of_lt xpos (by omega)]; omega | ||
· rw [Int.add_emod_self.symm, Int.emod_eq_of_lt (by omega) (by omega)]; omega |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It would be nice to learn how to extract out a reusable lemma from this, but I'm happy to leave that as a task we perform once we get some more experience with the API.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I moved this into Data/Int
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Overall LGTM, I register a place where I'd like to find an argument that goes through with a higher-level lemma.
uadd_overflow
,sadd_overflow
, uadd_overflow_eq
,sadd_overflow_eq
) and support theoremsBitVec.(uadd_overflow, sadd_overflow, uadd_overflow_eq, sadd_overflow_eq)
and support theorems
This PR adds SMT-LIB operators to detect overflow
BitVec.(uadd_overflow, sadd_overflow)
, according to the definitions here, and the theorems proving equivalence of such definitions with theBitVec
library functions (uaddOverflow_eq
,saddOverflow_eq
). Support theorems for these proofs areBitVec.toNat_mod_cancel_of_lt, BitVec.toInt_lt, BitVec.le_toInt, Int.bmod_neg_iff
. The PR also includes a set of tests.