;;; Copyright 2022 Intel Corporation All Rights Reserved. ;; Simple proofs of Sam Coward rules ;; Anna Slobodova 02/08/2022 (in-package "ACL2") (include-book "centaur/bitops/ihsext-basics" :dir :System) (local (include-book "arithmetic/top" :dir :system)) (local (include-book "ihs/quotient-remainder-lemmas" :dir :system)) ;; (local (include-book "std/strings/hexify" :dir :system)) (local (in-theory (disable unsigned-byte-p (tau-system)))) ;;------- Commutativity ;; For any r: follows from commutativity of integers (defthm bounded-commutativity-of-* (implies (and (integerp a) (integerp b)) (equal (loghead r (* a b)) (loghead r (* b a))))) ;; SOme lemmas that help us with further proofs (local (defthm unsigned-byte-p-of-mul (implies (and (unsigned-byte-p p a) (unsigned-byte-p r b)) (unsigned-byte-p (+ p r) (* a b))) :hints (("goal" :in-theory (enable unsigned-byte-p) :nonlinearp t)) )) ;; uses BITOPS::UNSIGNED-BYTE-P-INCR (local (defthm loghead-inc (implies (and (unsigned-byte-p n x) (natp m) (<= n m)) (equal (loghead m x) x)))) (local (defthm loghead-inc-of-mul (implies (and (force (unsigned-byte-p p a)) (force (unsigned-byte-p r b)) (natp p) (natp r) (natp u) (<= (+ p r) u)) (equal (loghead u (* a b)) (* a b) )) :hints (("goal" :in-theory (disable loghead-inc) :use ((:instance loghead-inc (m u) (n (+ p r)) (x (* a b)))) )) )) ;;------------------ MULT ASSOCIATIVITY -------------- ;; Our goal is to prove (under some conditions) ;; (equal ;; (loghead v (* (loghead u (* a b)) c)) ;; (loghead v (* a (loghead q (* b c ))))) ;; First let's simplify LHS: ;; consider two cases: ;;= (loghead v (* (loghead v (loghead u (* a b))) (loghead v c))) if (<= v u) ;;= (loghead v (* (* a b) c)) if (and (< u v)(<= (+ p r) u)) (local (encapsulate () (local (defthm bounded-mult-associativity-LHS1 (implies (and (integerp a) (integerp b) (integerp c) (natp u) (<= v u)) (equal (loghead v (* (loghead u (* a b)) c)) (loghead v (* (loghead v (* a b)) (loghead v c))))) :hints (("goal" :in-theory (disable BITOPS::LOGHEAD-OF-*-OF-LOGHEAD-SAME BITOPS::LOGHEAD-OF-LOGHEAD-1) :use ((:instance BITOPS::LOGHEAD-OF-*-OF-LOGHEAD-SAME (n v) (x (loghead u (* a b))) (y c)) (:instance BITOPS::LOGHEAD-OF-LOGHEAD-1 (m v) (n u) (x (* a b)))))) )) (local (defthm bounded-mult-associativity-LHS2 (implies (and (integerp a) (integerp b) (integerp c) (natp u) (<= v u)) (equal (loghead v (* (loghead v (* a b)) (loghead v c))) (loghead v (* a b c)))))) (local (in-theory (disable COMMUTATIVITY-OF-*))) (local (defthm bounded-mult-associativity-LHS3 (implies (and (integerp a) (integerp b) (integerp c) (natp u) (<= v u)) (equal (loghead v (* (loghead u (* a b)) c)) (loghead v (* a b c)))) :hints (("goal" :cases ((<= v u)) )) )) (defthm bounded-mult-associativity-LHS4 (implies (and (unsigned-byte-p p a) (unsigned-byte-p r b) (integerp c) (natp u) (natp v) (natp p) (natp r) (or (<= v u) (<= (+ p r) u))) (equal (loghead v (* (loghead u (* a b)) c)) (loghead v (* a b c))))) )) ;; Now let's simplify RHS (again consider two cases) ;;(loghead v (* a (loghead q (* b c)))) ;;= (loghead v (* (loghead v a) (loghead v (* b c)))) if (<= v q) ;;= (loghead v (* a (loghead (+ r s) (* b c)))) if (< q v) (<= (+ r s) q) ;; =(loghead v (* a (loghead v (* b c)))) ;; =(loghead v (* a (* b c))) (local (encapsulate () (local (defthm bounded-mult-associativity-RHS1 (implies (and (integerp a) (integerp b) (integerp c) (natp v) (natp q) (<= v q)) (equal (loghead v (* a (loghead q (* b c)))) (loghead v (* (loghead v a ) (loghead v (* b c)))))) :hints (("goal" :in-theory (disable BITOPS::LOGHEAD-OF-*-OF-LOGHEAD-SAME BITOPS::LOGHEAD-OF-LOGHEAD-1) :use ((:instance BITOPS::LOGHEAD-OF-*-OF-LOGHEAD-SAME (n v) (x a) (y (loghead q (* b c)))) (:instance BITOPS::LOGHEAD-OF-LOGHEAD-1 (m v) (n q) (x (* b c)))))) )) (local (defthm bounded-mult-associativity-RHS2 (implies (and (integerp a) (integerp b) (integerp c) (natp v) (natp q) (<= v q)) (equal (loghead v (* (loghead v a ) (loghead v (* b c)))) (loghead v (* a b c)))))) (local (defthm bounded-mult-associativity-RHS3 (implies (and (integerp a) (integerp b) (integerp c) (natp v) (natp q) (<= v q)) (equal (loghead v (* a (loghead q (* b c)))) (loghead v (* a b c)))))) (defthm bounded-associativity-RHS4 (implies (and (unsigned-byte-p r b) (unsigned-byte-p s c) (integerp a) (natp q) (natp v) (natp r) (natp s) (or (<= v q) (<= (+ r s) q))) (equal (loghead v (* a (loghead q (* b c)))) (loghead v (* a b c))))) )) (defthm bounded-mult-associativity (implies (and (unsigned-byte-p p a) (unsigned-byte-p r b) (unsigned-byte-p s c) (natp p)(natp r) (natp s)(natp u) (natp v)(natp q) (and (or (<= v q) (<= (+ r s) q)) (or (<= v u) (<= (+ p r) u)))) (equal (loghead v (* (loghead u (* a b)) c)) (loghead v (* a (loghead q (* b c ))))) )) ;;---------- ADD ASSOCIATIVITY LEFT OUT #|| (defthm bounded-add-associativity (implies (and (unsigned-byte-p p a) (unsigned-byte-p r b) (unsigned-byte-p s c) (and (or (<= v q) (< (max r s) q)) (or (<= v u) (< (max p r) u)))) (equal (loghead v (+ (loghead u (+ a b)) c)) (loghead v (+ a (loghead q (+ b c))))))) ||# ;;------------- DISTRIBUTE ;; We want to prove (under some conditions) (local (encapsulate () ;; (loghead r (* a (loghead q (+ b c)))) ;; (loghead r (* (loghead r a) (loghead r (loghead q (+ b c))))) ;; (loghead r (* (loghead r a) (loghead r (+ b c)))) ;; (loghead r (* (loghead r a) (loghead r (+ (loghead r b) (loghead r c))))) (local (defthm distribute-mult-over-add-LHS1 (implies (and (integerp a) (integerp b) (integerp c) (natp q) (<= r q)) (equal (loghead r (* a (loghead q (+ b c)))) (loghead r (* (loghead r a) (loghead r (+ b c)))) )) :hints (("goal" :in-theory (disable BITOPS::LOGHEAD-OF-*-OF-LOGHEAD-SAME BITOPS::LOGHEAD-OF-LOGHEAD-1 ) :use ((:instance BITOPS::LOGHEAD-OF-*-OF-LOGHEAD-SAME (n r) (x a) (y (loghead q (+ b c)))) (:instance BITOPS::LOGHEAD-OF-LOGHEAD-1 (m r) (n q) (x (+ b c))) ) )))) (local (defthm distribute-mult-over-add-LHS2 (implies (and (integerp a) (integerp b) (integerp c) (natp q) (<= r q)) (equal (loghead r (* (loghead r a) (loghead r (+ b c)))) (loghead r (* a (+ b c))) )))) (defthm distribute-mult-over-add-LHS3 (implies (and (integerp a) (integerp b) (integerp c) (natp q) (<= r q)) (equal (loghead r (* a (loghead q (+ b c)))) (loghead r (* a (+ b c))) ))) )) (local (encapsulate () (local (defthm distribute-mult-over-add-RHS1 (implies (and (integerp a) (integerp b) (integerp c) (natp u) (natp v) (<= r u) (<= r v)) (equal (loghead r (+ (loghead u (* a b)) (loghead v (* a c)))) (loghead r (+ (loghead r (* a b)) (loghead r (* a c)))) )) :hints (("goal" :in-theory (disable BITOPS::LOGHEAD-OF-+-OF-LOGHEAD-SAME BITOPS::LOGHEAD-OF-LOGHEAD-1 ) :use ((:instance BITOPS::LOGHEAD-OF-+-OF-LOGHEAD-SAME (n r) (x (loghead u (* a b))) (y (loghead v (* a c)))) (:instance BITOPS::LOGHEAD-OF-LOGHEAD-1 (m r) (n u) (x (* a b))) (:instance BITOPS::LOGHEAD-OF-LOGHEAD-1 (m r) (n v) (x (* a c))) ) ))) ) (local (defthm distribute-mult-over-add-RHS2 (implies (and (integerp a) (integerp b) (integerp c) (natp u) (natp v) (<= r u) (<= r v)) (equal (loghead r (+ (loghead r (* a b)) (loghead r (* a c)))) (loghead r (+ (* a b) (* a c))) )))) (defthm distribute-mult-over-add-RHS3 (implies (and (integerp a) (integerp b) (integerp c) (natp u) (natp v) (<= r u) (<= r v)) (equal (loghead r (+ (loghead u (* a b)) (loghead v (* a c)))) (loghead r (+ (* a b) (* a c))) ))) )) (defthm distribute-mult-over-add (implies (and (integerp a) (integerp b) (integerp c) (natp q) (natp u) (natp v) (<= r q) (<= r u) (<= r v)) (equal (loghead r (* a (loghead q (+ b c)))) (loghead r (+ (loghead u (* a b)) (loghead v (* a c)))))) :hints (("goal" :in-theory (disable distribute-mult-over-add-LHS3 ) :use ( distribute-mult-over-add-LHS3) )) ) ;;------------- Sum Same (encapsulate () (local (defthm lemma1 (implies (integerp a) (equal (+ a a) (* 2 a))))) (defthm bounded-sum-same (implies (integerp a) (equal (loghead q (+ a a)) (loghead q (* 2 a))))) ) ;;--------------- Add Zero (defthm bounded-add-zero (implies (and (integerp a) (integerp b) (natp p) (equal (mod b (expt 2 p)) 0)) (equal (loghead p (+ a b)) (loghead p a))) :hints (("goal" :in-theory (enable loghead))) ) ;;------------- Sub to Neg ;; no rules are created from this theorem (defthm sub-to-neg (implies (and (integerp a) (integerp b)) (equal (loghead r (- a b)) (loghead r (+ a (- b))))) :rule-classes nil ) ;;----------- Mult by One (defthm mult-by-one (implies (and (integerp a) (integerp b) (natp p) (equal (mod b (expt 2 p)) 1)) (equal (loghead p (* a b)) (loghead p a))) :hints (("goal" :in-theory (enable loghead))) ) ;;------------ Mult by Two (defthm bounded-mult-by-two (implies (integerp a) (equal (loghead r (* a 2)) (loghead r (ash a 1)))) :hints(("goal" :in-theory (Enable ash))) ) ;;------------ Merge Left Shift ;; -- more general (defthm merge-left-shift (implies (and (integerp a) (natp b) (natp c)) (equal (ash (ash a b) c) (ash a (+ b c)))) :hints (("goal" :in-theory (enable ash))) ) ;;----------- Merg Right Shift ;; -- mode general (defthm merge-right-shift (implies (and (integerp a) (natp b) (natp c)) (equal (ash (ash a (- b)) (- c)) (ash a (- (+ b c)))))) ;;---------- Redundant Sel (defthm redundant-sel (equal (if b a a) a) :rule-classes nil) ;; not true: (r=10, p=2, a=3=b011,~a=b110, -a=-3=b101, r=3) ;; (defthm bounded-not-neg ;; (implies ;; (and ;; (unsigned-byte-p p a) ;; (natp p)) ;; (equal ;; (loghead r (+ 1 (loghead p (lognot a)))) ;; (loghead r (- a)))) ;; :hints (("goal" :in-theory (Enable lognot))) ;; ) ;; (defthm bounded-neg-not ;; (implies ;; (and ;; (natp p) ;; (natp r) ;; (<= r p) ;; (unsigned-byte-p p a) ;; ) ;; (equal ;; (loghead r (+ 1 (loghead p (lognot a)))) ;; (loghead r (- a)))) ;; :hints (("goal" :in-theory (Enable lognot))) ;; ) ;;---------- Not over Con ;;-- more general -- ;; (logapp s b a) will concatenate a and low s bits of b (defthm not-over-con (implies (and (unsigned-byte-p q a) (unsigned-byte-p s b) ) (equal (loghead (+ s q) (lognot (logapp s b a))) (loghead (+ s q) (logapp s (lognot b) (lognot a))))) :hints (("goal" :in-theory (enable logapp lognot loghead expt mod unsigned-byte-p) :nonlinearp t)) ) ;;-------------- Mult Constant (defthm mult-constant (implies (and (integerp x) (integerp c)) (equal (+ (* 2 (* (logtail 1 c) x)) (* (loghead 1 c) x)) (* c x))) :hints (("goal" :nonlinearp t :in-theory (Enable loghead logtail) )) ) ;;------------- One to Two Mult (defthm mult-to-two (implies (integerp x) (equal (- (* 2 x) x) x))) ;;------------ Left Shift Add (defthm left-shift-add (implies (and (natp c) (integerp a) (integerp b)) (equal (ash (+ a b) c) (+ (ash a c) (ash b c)))) :hints (("goal" :in-theory (Enable ash))) ) ;;------------- Right Shift Add (defthm add-right-shift (implies (and (integerp a) (integerp b) (natp c)) (equal (ash (+ (ash a c) b) (- c)) (+ a (ash b (- c))))) :hints (("goal" :in-theory (Enable ash))) ) ;;-------------- Left Shift Mul (defthm left-shift-mult (implies (and (integerp a) (integerp b) (natp c)) (equal (ash (* a b) c) (* (ash a c) b))) :hints (("goal" :in-theory (Enable ash))) ) ;;-------------- Sel Add ;; (defthm bounded-sel-add ;; (implies ;; (and ;; (unsigned-byte-p p a) ;; (unsigned-byte-p q b) ;; (unsigned-byte-p p c) ;; (unsigned-byte-p q d) ;; ) ;; (equal ;; (loghead r (if e (+ a b) (+ c d))) ;; (loghead r (+ (if e a c) (if e b d)))))) ;; ;;-- more general --- ;; In acl2, (if e x y) will evaluate to y only if e=NIL, otherwise it evaluates to x (defthm sel-add (implies (and (integerp a) (integerp b) (integerp c) (integerp d) ) (equal (if e (+ a b) (+ c d)) (+ (if e a c) (if e b d))))) ;;-------- Sel Add Zero ;; this is jsut a case of the previous one. (defthm sel-add-zero (implies (and (integerp a) (integerp b) (integerp c)) (equal (if e (+ a b) c) (+ (if e a c) (if e b 0))))) ;;------- Mov Sel Zero ;; (defthm mov-sel-zero ;; (implies ;; (and ;; (integerp a) ;; (integerp c)) ;; (equal ;; (loghead r (* (if b 0 a) c)) ;; (loghead r (* a (if b 0 c)))))) ;; ;;--- More general-- (defthm mov-sel-zero (implies (and (integerp a) (integerp c)) (equal (* (if b 0 a) c) (* a (if b 0 c))))) ;;------------- Concat to Add ;; (str::hexify (logapp 16 #uxCDEF #uxAB)) ;;more general (defthm bounded-concat-to-add (implies (and (integerp a) (unsigned-byte-p q b) (natp q)) (equal (logapp q b a) (+ (ash a q) b))) :hints (("goal" :in-theory (enable ash logapp unsigned-byte-p))) )