{-# LANGUAGE DataKinds #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE KindSignatures #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE TypeApplications #-}
{-# LANGUAGE TypeOperators #-}
module What4.Utils.BVDomain.Arith
( Domain(..)
, proper
, bvdMask
, member
, pmember
, interval
, size
, asSingleton
, ubounds
, sbounds
, eq
, slt
, ult
, domainsOverlap
, arithDomainData
, bitbounds
, unknowns
, fillright
, any
, singleton
, range
, fromAscEltList
, union
, concat
, select
, zext
, sext
, shl
, lshr
, ashr
, add
, negate
, scale
, mul
, udiv
, urem
, sdiv
, srem
, What4.Utils.BVDomain.Arith.not
, genDomain
, genElement
, genPair
, correct_any
, correct_ubounds
, correct_sbounds
, correct_singleton
, correct_overlap
, correct_union
, correct_zero_ext
, correct_sign_ext
, correct_concat
, correct_shrink
, correct_trunc
, correct_select
, correct_add
, correct_neg
, correct_mul
, correct_scale
, correct_scale_eq
, correct_udiv
, correct_urem
, correct_sdivRange
, correct_sdiv
, correct_srem
, correct_not
, correct_shl
, correct_lshr
, correct_ashr
, correct_eq
, correct_ult
, correct_slt
, correct_unknowns
, correct_bitbounds
) where
import qualified Data.Bits as Bits
import Data.Bits hiding (testBit, xor)
import Data.Parameterized.NatRepr
import GHC.TypeNats
import GHC.Stack
import qualified Prelude
import Prelude hiding (any, concat, negate, and, or, not)
import Test.Verification ( Property, property, (==>), Gen, chooseInteger )
data Domain (w :: Nat)
= BVDAny !Integer
| BVDInterval !Integer !Integer !Integer
deriving Int -> Domain w -> ShowS
[Domain w] -> ShowS
Domain w -> String
(Int -> Domain w -> ShowS)
-> (Domain w -> String) -> ([Domain w] -> ShowS) -> Show (Domain w)
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
forall (w :: Nat). Int -> Domain w -> ShowS
forall (w :: Nat). [Domain w] -> ShowS
forall (w :: Nat). Domain w -> String
showList :: [Domain w] -> ShowS
$cshowList :: forall (w :: Nat). [Domain w] -> ShowS
show :: Domain w -> String
$cshow :: forall (w :: Nat). Domain w -> String
showsPrec :: Int -> Domain w -> ShowS
$cshowsPrec :: forall (w :: Nat). Int -> Domain w -> ShowS
Show
sameDomain :: Domain w -> Domain w -> Bool
sameDomain :: Domain w -> Domain w -> Bool
sameDomain (BVDAny Integer
_) (BVDAny Integer
_) = Bool
True
sameDomain (BVDInterval Integer
_ Integer
x Integer
w) (BVDInterval Integer
_ Integer
x' Integer
w') = Integer
x Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
x' Bool -> Bool -> Bool
&& Integer
w Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
w'
sameDomain Domain w
_ Domain w
_ = Bool
False
size :: Domain w -> Integer
size :: Domain w -> Integer
size (BVDAny Integer
mask) = Integer
mask Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
1
size (BVDInterval Integer
_ Integer
_ Integer
sz) = Integer
sz Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
1
member :: Domain w -> Integer -> Bool
member :: Domain w -> Integer -> Bool
member (BVDAny Integer
_) Integer
_ = Bool
True
member (BVDInterval Integer
mask Integer
lo Integer
sz) Integer
x = ((Integer
x' Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
lo) Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Integer
mask) Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
<= Integer
sz
where x' :: Integer
x' = Integer
x Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Integer
mask
proper :: NatRepr w -> Domain w -> Bool
proper :: NatRepr w -> Domain w -> Bool
proper NatRepr w
w (BVDAny Integer
mask) = Integer
mask Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== NatRepr w -> Integer
forall (w :: Nat). NatRepr w -> Integer
maxUnsigned NatRepr w
w
proper NatRepr w
w (BVDInterval Integer
mask Integer
lo Integer
sz) =
Integer
mask Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== NatRepr w -> Integer
forall (w :: Nat). NatRepr w -> Integer
maxUnsigned NatRepr w
w Bool -> Bool -> Bool
&&
Integer
lo Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.|. Integer
mask Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
mask Bool -> Bool -> Bool
&&
Integer
sz Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.|. Integer
mask Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
mask Bool -> Bool -> Bool
&&
Integer
sz Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
mask
bvdMask :: Domain w -> Integer
bvdMask :: Domain w -> Integer
bvdMask Domain w
x =
case Domain w
x of
BVDAny Integer
mask -> Integer
mask
BVDInterval Integer
mask Integer
_ Integer
_ -> Integer
mask
genDomain :: NatRepr w -> Gen (Domain w)
genDomain :: NatRepr w -> Gen (Domain w)
genDomain NatRepr w
w =
do let mask :: Integer
mask = NatRepr w -> Integer
forall (w :: Nat). NatRepr w -> Integer
maxUnsigned NatRepr w
w
Integer
lo <- (Integer, Integer) -> Gen Integer
chooseInteger (Integer
0, Integer
mask)
Integer
sz <- (Integer, Integer) -> Gen Integer
chooseInteger (Integer
0, Integer
mask)
Domain w -> Gen (Domain w)
forall (f :: Type -> Type) a. Applicative f => a -> f a
pure (Domain w -> Gen (Domain w)) -> Domain w -> Gen (Domain w)
forall a b. (a -> b) -> a -> b
$! Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
lo Integer
sz
genElement :: Domain w -> Gen Integer
genElement :: Domain w -> Gen Integer
genElement (BVDAny Integer
mask) = (Integer, Integer) -> Gen Integer
chooseInteger (Integer
0, Integer
mask)
genElement (BVDInterval Integer
mask Integer
lo Integer
sz) =
do Integer
x <- (Integer, Integer) -> Gen Integer
chooseInteger (Integer
0, Integer
sz)
Integer -> Gen Integer
forall (f :: Type -> Type) a. Applicative f => a -> f a
pure ((Integer
xInteger -> Integer -> Integer
forall a. Num a => a -> a -> a
+Integer
lo) Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Integer
mask)
genPair :: NatRepr w -> Gen (Domain w, Integer)
genPair :: NatRepr w -> Gen (Domain w, Integer)
genPair NatRepr w
w =
do Domain w
a <- NatRepr w -> Gen (Domain w)
forall (w :: Nat). NatRepr w -> Gen (Domain w)
genDomain NatRepr w
w
Integer
x <- Domain w -> Gen Integer
forall (w :: Nat). Domain w -> Gen Integer
genElement Domain w
a
(Domain w, Integer) -> Gen (Domain w, Integer)
forall (m :: Type -> Type) a. Monad m => a -> m a
return (Domain w
a,Integer
x)
halfRange :: (1 <= w) => NatRepr w -> Integer
halfRange :: NatRepr w -> Integer
halfRange NatRepr w
w = Int -> Integer
forall a. Bits a => Int -> a
bit (NatRepr w -> Int
forall (n :: Nat). NatRepr n -> Int
widthVal NatRepr w
w Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
1)
asSingleton :: Domain w -> Maybe Integer
asSingleton :: Domain w -> Maybe Integer
asSingleton Domain w
x =
case Domain w
x of
BVDAny Integer
_ -> Maybe Integer
forall a. Maybe a
Nothing
BVDInterval Integer
_ Integer
xl Integer
xd
| Integer
xd Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
0 -> Integer -> Maybe Integer
forall a. a -> Maybe a
Just Integer
xl
| Bool
otherwise -> Maybe Integer
forall a. Maybe a
Nothing
isSingletonZero :: Domain w -> Bool
isSingletonZero :: Domain w -> Bool
isSingletonZero Domain w
x =
case Domain w
x of
BVDInterval Integer
_ Integer
0 Integer
0 -> Bool
True
Domain w
_ -> Bool
False
isBVDAny :: Domain w -> Bool
isBVDAny :: Domain w -> Bool
isBVDAny Domain w
x =
case Domain w
x of
BVDAny {} -> Bool
True
BVDInterval {} -> Bool
False
ubounds :: Domain w -> (Integer, Integer)
ubounds :: Domain w -> (Integer, Integer)
ubounds Domain w
a =
case Domain w
a of
BVDAny Integer
mask -> (Integer
0, Integer
mask)
BVDInterval Integer
mask Integer
al Integer
aw
| Integer
ah Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
> Integer
mask -> (Integer
0, Integer
mask)
| Bool
otherwise -> (Integer
al, Integer
ah)
where ah :: Integer
ah = Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw
sbounds :: (1 <= w) => NatRepr w -> Domain w -> (Integer, Integer)
sbounds :: NatRepr w -> Domain w -> (Integer, Integer)
sbounds NatRepr w
w Domain w
a = (Integer
lo Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
delta, Integer
hi Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
delta)
where
delta :: Integer
delta = NatRepr w -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer
halfRange NatRepr w
w
(Integer
lo, Integer
hi) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds (Domain w -> Domain w -> Domain w
forall (w :: Nat). (1 <= w) => Domain w -> Domain w -> Domain w
add Domain w
a (Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
BVDInterval (Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a) Integer
delta Integer
0))
arithDomainData :: Domain w -> Maybe (Integer, Integer)
arithDomainData :: Domain w -> Maybe (Integer, Integer)
arithDomainData (BVDAny Integer
_) = Maybe (Integer, Integer)
forall a. Maybe a
Nothing
arithDomainData (BVDInterval Integer
_ Integer
al Integer
aw) = (Integer, Integer) -> Maybe (Integer, Integer)
forall a. a -> Maybe a
Just (Integer
al, Integer
aw)
domainsOverlap :: Domain w -> Domain w -> Bool
domainsOverlap :: Domain w -> Domain w -> Bool
domainsOverlap Domain w
a Domain w
b =
case Domain w
a of
BVDAny Integer
_ -> Bool
True
BVDInterval Integer
_ Integer
al Integer
aw ->
case Domain w
b of
BVDAny Integer
_ -> Bool
True
BVDInterval Integer
mask Integer
bl Integer
bw ->
Integer
diff Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
<= Integer
bw Bool -> Bool -> Bool
|| Integer
diff Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
> Integer
mask
where diff :: Integer
diff = (Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
bl) Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Integer
mask
eq :: Domain w -> Domain w -> Maybe Bool
eq :: Domain w -> Domain w -> Maybe Bool
eq Domain w
a Domain w
b
| Just Integer
x <- Domain w -> Maybe Integer
forall (w :: Nat). Domain w -> Maybe Integer
asSingleton Domain w
a
, Just Integer
y <- Domain w -> Maybe Integer
forall (w :: Nat). Domain w -> Maybe Integer
asSingleton Domain w
b = Bool -> Maybe Bool
forall a. a -> Maybe a
Just (Integer
x Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
y)
| Domain w -> Domain w -> Bool
forall (w :: Nat). Domain w -> Domain w -> Bool
domainsOverlap Domain w
a Domain w
b Bool -> Bool -> Bool
forall a. Eq a => a -> a -> Bool
== Bool
False = Bool -> Maybe Bool
forall a. a -> Maybe a
Just Bool
False
| Bool
otherwise = Maybe Bool
forall a. Maybe a
Nothing
slt :: (1 <= w) => NatRepr w -> Domain w -> Domain w -> Maybe Bool
slt :: NatRepr w -> Domain w -> Domain w -> Maybe Bool
slt NatRepr w
w Domain w
a Domain w
b
| Integer
a_max Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
b_min = Bool -> Maybe Bool
forall a. a -> Maybe a
Just Bool
True
| Integer
a_min Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
>= Integer
b_max = Bool -> Maybe Bool
forall a. a -> Maybe a
Just Bool
False
| Bool
otherwise = Maybe Bool
forall a. Maybe a
Nothing
where
(Integer
a_min, Integer
a_max) = NatRepr w -> Domain w -> (Integer, Integer)
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> (Integer, Integer)
sbounds NatRepr w
w Domain w
a
(Integer
b_min, Integer
b_max) = NatRepr w -> Domain w -> (Integer, Integer)
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> (Integer, Integer)
sbounds NatRepr w
w Domain w
b
ult :: (1 <= w) => Domain w -> Domain w -> Maybe Bool
ult :: Domain w -> Domain w -> Maybe Bool
ult Domain w
a Domain w
b
| Integer
a_max Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
b_min = Bool -> Maybe Bool
forall a. a -> Maybe a
Just Bool
True
| Integer
a_min Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
>= Integer
b_max = Bool -> Maybe Bool
forall a. a -> Maybe a
Just Bool
False
| Bool
otherwise = Maybe Bool
forall a. Maybe a
Nothing
where
(Integer
a_min, Integer
a_max) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
a
(Integer
b_min, Integer
b_max) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
b
any :: (1 <= w) => NatRepr w -> Domain w
any :: NatRepr w -> Domain w
any NatRepr w
w = Integer -> Domain w
forall (w :: Nat). Integer -> Domain w
BVDAny (NatRepr w -> Integer
forall (w :: Nat). NatRepr w -> Integer
maxUnsigned NatRepr w
w)
singleton :: (HasCallStack, 1 <= w) => NatRepr w -> Integer -> Domain w
singleton :: NatRepr w -> Integer -> Domain w
singleton NatRepr w
w Integer
x = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
BVDInterval Integer
mask (Integer
x Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Integer
mask) Integer
0
where mask :: Integer
mask = NatRepr w -> Integer
forall (w :: Nat). NatRepr w -> Integer
maxUnsigned NatRepr w
w
range :: NatRepr w -> Integer -> Integer -> Domain w
range :: NatRepr w -> Integer -> Integer -> Domain w
range NatRepr w
w Integer
al Integer
ah = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
al ((Integer
ah Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
al) Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Integer
mask)
where mask :: Integer
mask = NatRepr w -> Integer
forall (w :: Nat). NatRepr w -> Integer
maxUnsigned NatRepr w
w
interval :: Integer -> Integer -> Integer -> Domain w
interval :: Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
al Integer
aw =
if Integer
aw Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
>= Integer
mask then Integer -> Domain w
forall (w :: Nat). Integer -> Domain w
BVDAny Integer
mask else Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
BVDInterval Integer
mask (Integer
al Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Integer
mask) Integer
aw
fromAscEltList :: (1 <= w) => NatRepr w -> [Integer] -> Domain w
fromAscEltList :: NatRepr w -> [Integer] -> Domain w
fromAscEltList NatRepr w
w [] = NatRepr w -> Integer -> Domain w
forall (w :: Nat).
(HasCallStack, 1 <= w) =>
NatRepr w -> Integer -> Domain w
singleton NatRepr w
w Integer
0
fromAscEltList NatRepr w
w [Integer
x] = NatRepr w -> Integer -> Domain w
forall (w :: Nat).
(HasCallStack, 1 <= w) =>
NatRepr w -> Integer -> Domain w
singleton NatRepr w
w Integer
x
fromAscEltList NatRepr w
w (Integer
x0 : Integer
x1 : [Integer]
xs) = (Integer, Integer) -> (Integer, Integer) -> [Integer] -> Domain w
go (Integer
x0, Integer
x0) (Integer
x1, Integer
x1) [Integer]
xs
where
go :: (Integer, Integer) -> (Integer, Integer) -> [Integer] -> Domain w
go (Integer
a, Integer
b) (Integer
c, Integer
d) [] = Domain w -> Domain w -> Domain w
forall (w :: Nat). (1 <= w) => Domain w -> Domain w -> Domain w
union (NatRepr w -> Integer -> Integer -> Domain w
forall (w :: Nat). NatRepr w -> Integer -> Integer -> Domain w
range NatRepr w
w Integer
a Integer
b) (NatRepr w -> Integer -> Integer -> Domain w
forall (w :: Nat). NatRepr w -> Integer -> Integer -> Domain w
range NatRepr w
w Integer
c Integer
d)
go (Integer
a, Integer
b) (Integer
c, Integer
d) (Integer
e : [Integer]
rest)
| Integer
e Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
d Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
> Integer
c Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
b = (Integer, Integer) -> (Integer, Integer) -> [Integer] -> Domain w
go (Integer
a, Integer
d) (Integer
e, Integer
e) [Integer]
rest
| Bool
otherwise = (Integer, Integer) -> (Integer, Integer) -> [Integer] -> Domain w
go (Integer
a, Integer
b) (Integer
c, Integer
e) [Integer]
rest
union :: (1 <= w) => Domain w -> Domain w -> Domain w
union :: Domain w -> Domain w -> Domain w
union Domain w
a Domain w
b =
case Domain w
a of
BVDAny Integer
_ -> Domain w
a
BVDInterval Integer
_ Integer
al Integer
aw ->
case Domain w
b of
BVDAny Integer
_ -> Domain w
b
BVDInterval Integer
mask Integer
bl Integer
bw ->
Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
cl (Integer
ch Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
cl)
where
sz :: Integer
sz = Integer
mask Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
1
ac :: Integer
ac = Integer
2 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw
bc :: Integer
bc = Integer
2 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
bl Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
bw
al' :: Integer
al' = if Integer
ac Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
mask Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
bc then Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
sz else Integer
al
bl' :: Integer
bl' = if Integer
bc Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
mask Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
ac then Integer
bl Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
sz else Integer
bl
ah' :: Integer
ah' = Integer
al' Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw
bh' :: Integer
bh' = Integer
bl' Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
bw
cl :: Integer
cl = Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min Integer
al' Integer
bl'
ch :: Integer
ch = Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max Integer
ah' Integer
bh'
concat :: NatRepr u -> Domain u -> NatRepr v -> Domain v -> Domain (u + v)
concat :: NatRepr u -> Domain u -> NatRepr v -> Domain v -> Domain (u + v)
concat NatRepr u
u Domain u
a NatRepr v
v Domain v
b =
case Domain u
a of
BVDAny Integer
_ -> Integer -> Domain (u + v)
forall (w :: Nat). Integer -> Domain w
BVDAny Integer
mask
BVDInterval Integer
_ Integer
al Integer
aw -> Integer -> Integer -> Integer -> Domain (u + v)
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask (Integer -> Integer -> Integer
cat Integer
al Integer
bl) (Integer -> Integer -> Integer
cat Integer
aw Integer
bw)
where
cat :: Integer -> Integer -> Integer
cat Integer
i Integer
j = (Integer
i Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftL` NatRepr v -> Int
forall (n :: Nat). NatRepr n -> Int
widthVal NatRepr v
v) Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
j
mask :: Integer
mask = NatRepr (u + v) -> Integer
forall (w :: Nat). NatRepr w -> Integer
maxUnsigned (NatRepr u -> NatRepr v -> NatRepr (u + v)
forall (m :: Nat) (n :: Nat).
NatRepr m -> NatRepr n -> NatRepr (m + n)
addNat NatRepr u
u NatRepr v
v)
(Integer
bl, Integer
bh) = Domain v -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain v
b
bw :: Integer
bw = Integer
bh Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
bl
shrink ::
NatRepr i ->
Domain (i + n) -> Domain n
shrink :: NatRepr i -> Domain (i + n) -> Domain n
shrink NatRepr i
i Domain (i + n)
a =
case Domain (i + n)
a of
BVDAny Integer
mask -> Integer -> Domain n
forall (w :: Nat). Integer -> Domain w
BVDAny (Integer -> Integer
shr Integer
mask)
BVDInterval Integer
mask Integer
al Integer
aw ->
Integer -> Integer -> Integer -> Domain n
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval (Integer -> Integer
shr Integer
mask) Integer
bl (Integer
bh Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
bl)
where
bl :: Integer
bl = Integer -> Integer
shr Integer
al
bh :: Integer
bh = Integer -> Integer
shr (Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw)
where
shr :: Integer -> Integer
shr Integer
x = Integer
x Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` NatRepr i -> Int
forall (n :: Nat). NatRepr n -> Int
widthVal NatRepr i
i
trunc ::
(n <= w) =>
NatRepr n ->
Domain w -> Domain n
trunc :: NatRepr n -> Domain w -> Domain n
trunc NatRepr n
n Domain w
a =
case Domain w
a of
BVDAny Integer
_ -> Integer -> Domain n
forall (w :: Nat). Integer -> Domain w
BVDAny Integer
mask
BVDInterval Integer
_ Integer
al Integer
aw -> Integer -> Integer -> Integer -> Domain n
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
al Integer
aw
where
mask :: Integer
mask = NatRepr n -> Integer
forall (w :: Nat). NatRepr w -> Integer
maxUnsigned NatRepr n
n
select ::
(1 <= n, i + n <= w) =>
NatRepr i ->
NatRepr n ->
Domain w -> Domain n
select :: NatRepr i -> NatRepr n -> Domain w -> Domain n
select NatRepr i
i NatRepr n
n Domain w
a = NatRepr i -> Domain (i + n) -> Domain n
forall (i :: Nat) (n :: Nat).
NatRepr i -> Domain (i + n) -> Domain n
shrink NatRepr i
i (NatRepr (i + n) -> Domain w -> Domain (i + n)
forall (n :: Nat) (w :: Nat).
(n <= w) =>
NatRepr n -> Domain w -> Domain n
trunc (NatRepr i -> NatRepr n -> NatRepr (i + n)
forall (m :: Nat) (n :: Nat).
NatRepr m -> NatRepr n -> NatRepr (m + n)
addNat NatRepr i
i NatRepr n
n) Domain w
a)
zext :: (1 <= w, w+1 <= u) => Domain w -> NatRepr u -> Domain u
zext :: Domain w -> NatRepr u -> Domain u
zext Domain w
a NatRepr u
u = NatRepr u -> Integer -> Integer -> Domain u
forall (w :: Nat). NatRepr w -> Integer -> Integer -> Domain w
range NatRepr u
u Integer
al Integer
ah
where (Integer
al, Integer
ah) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
a
sext ::
forall w u. (1 <= w, w + 1 <= u) =>
NatRepr w ->
Domain w ->
NatRepr u ->
Domain u
sext :: NatRepr w -> Domain w -> NatRepr u -> Domain u
sext NatRepr w
w Domain w
a NatRepr u
u =
case LeqProof 1 u
fProof of
LeqProof 1 u
LeqProof ->
NatRepr u -> Integer -> Integer -> Domain u
forall (w :: Nat). NatRepr w -> Integer -> Integer -> Domain w
range NatRepr u
u Integer
al Integer
ah
where (Integer
al, Integer
ah) = NatRepr w -> Domain w -> (Integer, Integer)
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> (Integer, Integer)
sbounds NatRepr w
w Domain w
a
where
wProof :: LeqProof 1 w
wProof :: LeqProof 1 w
wProof = LeqProof 1 w
forall (m :: Nat) (n :: Nat). (m <= n) => LeqProof m n
LeqProof
uProof :: LeqProof (w+1) u
uProof :: LeqProof (w + 1) u
uProof = LeqProof (w + 1) u
forall (m :: Nat) (n :: Nat). (m <= n) => LeqProof m n
LeqProof
fProof :: LeqProof 1 u
fProof :: LeqProof 1 u
fProof = LeqProof 1 (w + 1) -> LeqProof (w + 1) u -> LeqProof 1 u
forall (m :: Nat) (n :: Nat) (p :: Nat).
LeqProof m n -> LeqProof n p -> LeqProof m p
leqTrans (LeqProof 1 w -> NatRepr 1 -> LeqProof 1 (w + 1)
forall (f :: Nat -> Type) (m :: Nat) (n :: Nat) (p :: Nat).
LeqProof m n -> f p -> LeqProof m (n + p)
leqAdd LeqProof 1 w
wProof (NatRepr 1
forall (n :: Nat). KnownNat n => NatRepr n
knownNat :: NatRepr 1)) LeqProof (w + 1) u
uProof
shl :: (1 <= w) => NatRepr w -> Domain w -> Domain w -> Domain w
shl :: NatRepr w -> Domain w -> Domain w -> Domain w
shl NatRepr w
w Domain w
a Domain w
b
| Domain w -> Bool
forall (w :: Nat). Domain w -> Bool
isBVDAny Domain w
a = Domain w
a
| Domain w -> Bool
forall (w :: Nat). Domain w -> Bool
isSingletonZero Domain w
a = Domain w
a
| Domain w -> Bool
forall (w :: Nat). Domain w -> Bool
isSingletonZero Domain w
b = Domain w
a
| Bool
otherwise = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
lo (Integer
hi Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
lo)
where
mask :: Integer
mask = Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a
sz :: Integer
sz = Integer
mask Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
1
(Integer
bl, Integer
bh) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
b
bl' :: Int
bl' = NatRepr w -> Integer -> Int
forall (w :: Nat). NatRepr w -> Integer -> Int
clamp NatRepr w
w Integer
bl
bh' :: Int
bh' = NatRepr w -> Integer -> Int
forall (w :: Nat). NatRepr w -> Integer -> Int
clamp NatRepr w
w Integer
bh
cl :: Integer
cl = if (Integer
mask Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` Int
bl' Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
0) then Integer
sz else Int -> Integer
forall a. Bits a => Int -> a
bit Int
bl'
ch :: Integer
ch = if (Integer
mask Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` Int
bh' Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
0) then Integer
sz else Int -> Integer
forall a. Bits a => Int -> a
bit Int
bh'
(Integer
lo, Integer
hi) = (Integer, Integer) -> (Integer, Integer) -> (Integer, Integer)
mulRange (Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
zbounds Domain w
a) (Integer
cl, Integer
ch)
lshr :: (1 <= w) => NatRepr w -> Domain w -> Domain w -> Domain w
lshr :: NatRepr w -> Domain w -> Domain w -> Domain w
lshr NatRepr w
w Domain w
a Domain w
b = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
cl (Integer
ch Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
cl)
where
mask :: Integer
mask = Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a
(Integer
al, Integer
ah) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
a
(Integer
bl, Integer
bh) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
b
cl :: Integer
cl = Integer
al Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` NatRepr w -> Integer -> Int
forall (w :: Nat). NatRepr w -> Integer -> Int
clamp NatRepr w
w Integer
bh
ch :: Integer
ch = Integer
ah Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` NatRepr w -> Integer -> Int
forall (w :: Nat). NatRepr w -> Integer -> Int
clamp NatRepr w
w Integer
bl
ashr :: (1 <= w) => NatRepr w -> Domain w -> Domain w -> Domain w
ashr :: NatRepr w -> Domain w -> Domain w -> Domain w
ashr NatRepr w
w Domain w
a Domain w
b = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
cl (Integer
ch Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
cl)
where
mask :: Integer
mask = Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a
(Integer
al, Integer
ah) = NatRepr w -> Domain w -> (Integer, Integer)
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> (Integer, Integer)
sbounds NatRepr w
w Domain w
a
(Integer
bl, Integer
bh) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
b
cl :: Integer
cl = Integer
al Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` (if Integer
al Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
0 then NatRepr w -> Integer -> Int
forall (w :: Nat). NatRepr w -> Integer -> Int
clamp NatRepr w
w Integer
bl else NatRepr w -> Integer -> Int
forall (w :: Nat). NatRepr w -> Integer -> Int
clamp NatRepr w
w Integer
bh)
ch :: Integer
ch = Integer
ah Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` (if Integer
ah Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
0 then NatRepr w -> Integer -> Int
forall (w :: Nat). NatRepr w -> Integer -> Int
clamp NatRepr w
w Integer
bh else NatRepr w -> Integer -> Int
forall (w :: Nat). NatRepr w -> Integer -> Int
clamp NatRepr w
w Integer
bl)
clamp :: NatRepr w -> Integer -> Int
clamp :: NatRepr w -> Integer -> Int
clamp NatRepr w
w Integer
x = Integer -> Int
forall a. Num a => Integer -> a
fromInteger (Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min (NatRepr w -> Integer
forall (w :: Nat). NatRepr w -> Integer
intValue NatRepr w
w) Integer
x)
add :: (1 <= w) => Domain w -> Domain w -> Domain w
add :: Domain w -> Domain w -> Domain w
add Domain w
a Domain w
b =
case Domain w
a of
BVDAny Integer
_ -> Domain w
a
BVDInterval Integer
_ Integer
al Integer
aw ->
case Domain w
b of
BVDAny Integer
_ -> Domain w
b
BVDInterval Integer
mask Integer
bl Integer
bw ->
Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask (Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
bl) (Integer
aw Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
bw)
negate :: (1 <= w) => Domain w -> Domain w
negate :: Domain w -> Domain w
negate Domain w
a =
case Domain w
a of
BVDAny Integer
_ -> Domain w
a
BVDInterval Integer
mask Integer
al Integer
aw -> Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
BVDInterval Integer
mask ((-Integer
ah) Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Integer
mask) Integer
aw
where ah :: Integer
ah = Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw
scale :: (1 <= w) => Integer -> Domain w -> Domain w
scale :: Integer -> Domain w -> Domain w
scale Integer
k Domain w
a
| Integer
k Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
0 = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
BVDInterval (Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a) Integer
0 Integer
0
| Integer
k Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
1 = Domain w
a
| Bool
otherwise =
case Domain w
a of
BVDAny Integer
_ -> Domain w
a
BVDInterval Integer
mask Integer
al Integer
aw
| Integer
k Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
>= Integer
0 -> Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask (Integer
k Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
al) (Integer
k Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
aw)
| Bool
otherwise -> Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask (Integer
k Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
ah) (Integer -> Integer
forall a. Num a => a -> a
abs Integer
k Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
aw)
where ah :: Integer
ah = Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw
mul :: (1 <= w) => Domain w -> Domain w -> Domain w
mul :: Domain w -> Domain w -> Domain w
mul Domain w
a Domain w
b
| Domain w -> Bool
forall (w :: Nat). Domain w -> Bool
isSingletonZero Domain w
a = Domain w
a
| Domain w -> Bool
forall (w :: Nat). Domain w -> Bool
isSingletonZero Domain w
b = Domain w
b
| Domain w -> Bool
forall (w :: Nat). Domain w -> Bool
isBVDAny Domain w
a = Domain w
a
| Domain w -> Bool
forall (w :: Nat). Domain w -> Bool
isBVDAny Domain w
b = Domain w
b
| Bool
otherwise = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
cl (Integer
ch Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
cl)
where
mask :: Integer
mask = Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a
(Integer
cl, Integer
ch) = (Integer, Integer) -> (Integer, Integer) -> (Integer, Integer)
mulRange (Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
zbounds Domain w
a) (Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
zbounds Domain w
b)
zbounds :: Domain w -> (Integer, Integer)
zbounds :: Domain w -> (Integer, Integer)
zbounds Domain w
a =
case Domain w
a of
BVDAny Integer
mask -> (Integer
0, Integer
mask)
BVDInterval Integer
mask Integer
lo Integer
sz -> (Integer
lo', Integer
lo' Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
sz)
where lo' :: Integer
lo' = if Integer
2Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
*Integer
lo Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
sz Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
> Integer
mask then Integer
lo Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- (Integer
mask Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
1) else Integer
lo
mulRange :: (Integer, Integer) -> (Integer, Integer) -> (Integer, Integer)
mulRange :: (Integer, Integer) -> (Integer, Integer) -> (Integer, Integer)
mulRange (Integer
al, Integer
ah) (Integer
bl, Integer
bh) = (Integer
cl, Integer
ch)
where
(Integer
albl, Integer
albh) = Integer -> (Integer, Integer) -> (Integer, Integer)
scaleRange Integer
al (Integer
bl, Integer
bh)
(Integer
ahbl, Integer
ahbh) = Integer -> (Integer, Integer) -> (Integer, Integer)
scaleRange Integer
ah (Integer
bl, Integer
bh)
cl :: Integer
cl = Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min Integer
albl Integer
ahbl
ch :: Integer
ch = Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max Integer
albh Integer
ahbh
scaleRange :: Integer -> (Integer, Integer) -> (Integer, Integer)
scaleRange :: Integer -> (Integer, Integer) -> (Integer, Integer)
scaleRange Integer
k (Integer
lo, Integer
hi)
| Integer
k Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
0 = (Integer
k Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
hi, Integer
k Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
lo)
| Bool
otherwise = (Integer
k Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
lo, Integer
k Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
hi)
udiv :: (1 <= w) => Domain w -> Domain w -> Domain w
udiv :: Domain w -> Domain w -> Domain w
udiv Domain w
a Domain w
b = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
ql (Integer
qh Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
ql)
where
mask :: Integer
mask = Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a
(Integer
al, Integer
ah) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
a
(Integer
bl, Integer
bh) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
b
ql :: Integer
ql = Integer
al Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`div` Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max Integer
1 Integer
bh
qh :: Integer
qh = Integer
ah Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`div` Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max Integer
1 Integer
bl
urem :: (1 <= w) => Domain w -> Domain w -> Domain w
urem :: Domain w -> Domain w -> Domain w
urem Domain w
a Domain w
b
| Integer
qh Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
ql = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
rl (Integer
rh Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
rl)
| Bool
otherwise = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
0 (Integer
bh Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
1)
where
mask :: Integer
mask = Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a
(Integer
al, Integer
ah) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
a
(Integer
bl, Integer
bh) = Domain w -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain w
b
(Integer
ql, Integer
rl) = Integer
al Integer -> Integer -> (Integer, Integer)
forall a. Integral a => a -> a -> (a, a)
`divMod` Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max Integer
1 Integer
bh
(Integer
qh, Integer
rh) = Integer
ah Integer -> Integer -> (Integer, Integer)
forall a. Integral a => a -> a -> (a, a)
`divMod` Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max Integer
1 Integer
bl
data ReciprocalRange = ReciprocalRange Integer Integer
rbounds :: (1 <= w) => NatRepr w -> Domain w -> ReciprocalRange
rbounds :: NatRepr w -> Domain w -> ReciprocalRange
rbounds NatRepr w
w Domain w
a =
case Domain w
a of
BVDAny Integer
_ -> Integer -> Integer -> ReciprocalRange
ReciprocalRange (-Integer
1) Integer
1
BVDInterval Integer
mask Integer
al Integer
aw
| Integer
ah Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
> Integer
mask Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
1 -> Integer -> Integer -> ReciprocalRange
ReciprocalRange (-Integer
1) Integer
1
| Bool
otherwise -> Integer -> Integer -> ReciprocalRange
ReciprocalRange (Integer -> Integer
signed (Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min Integer
mask Integer
ah)) (Integer -> Integer
signed (Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max Integer
1 Integer
al))
where
ah :: Integer
ah = Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw
signed :: Integer -> Integer
signed Integer
x = if Integer
x Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< NatRepr w -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer
halfRange NatRepr w
w then Integer
x else Integer
x Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- (Integer
mask Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
1)
sdivRange :: (Integer, Integer) -> ReciprocalRange -> (Integer, Integer)
sdivRange :: (Integer, Integer) -> ReciprocalRange -> (Integer, Integer)
sdivRange (Integer
al, Integer
ah) (ReciprocalRange Integer
bl Integer
bh) = (Integer
ql, Integer
qh)
where
(Integer
ql1, Integer
qh1) = (Integer, Integer) -> Integer -> (Integer, Integer)
scaleDownRange (Integer
al, Integer
ah) Integer
bh
(Integer
ql2, Integer
qh2) = (Integer, Integer) -> Integer -> (Integer, Integer)
scaleDownRange (Integer
al, Integer
ah) Integer
bl
ql :: Integer
ql = Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min Integer
ql1 Integer
ql2
qh :: Integer
qh = Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max Integer
qh1 Integer
qh2
scaleDownRange :: (Integer, Integer) -> Integer -> (Integer, Integer)
scaleDownRange :: (Integer, Integer) -> Integer -> (Integer, Integer)
scaleDownRange (Integer
lo, Integer
hi) Integer
k
| Integer
k Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
> Integer
0 = (Integer
lo Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`quot` Integer
k, Integer
hi Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`quot` Integer
k)
| Integer
k Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
0 = (Integer
hi Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`quot` Integer
k, Integer
lo Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`quot` Integer
k)
| Bool
otherwise = (Integer
lo, Integer
hi)
sdiv :: (1 <= w) => NatRepr w -> Domain w -> Domain w -> Domain w
sdiv :: NatRepr w -> Domain w -> Domain w -> Domain w
sdiv NatRepr w
w Domain w
a Domain w
b = Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
ql (Integer
qh Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
ql)
where
mask :: Integer
mask = Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a
(Integer
ql, Integer
qh) = (Integer, Integer) -> ReciprocalRange -> (Integer, Integer)
sdivRange (NatRepr w -> Domain w -> (Integer, Integer)
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> (Integer, Integer)
sbounds NatRepr w
w Domain w
a) (NatRepr w -> Domain w -> ReciprocalRange
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> ReciprocalRange
rbounds NatRepr w
w Domain w
b)
srem :: (1 <= w) => NatRepr w -> Domain w -> Domain w -> Domain w
srem :: NatRepr w -> Domain w -> Domain w -> Domain w
srem NatRepr w
w Domain w
a Domain w
b =
if Integer
ql Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
qh then
(if Integer
ql Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
0
then Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask (Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
ql Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
bl) (Integer
aw Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
ql Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
bw)
else Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask (Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
ql Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
bh) (Integer
aw Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
ql Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
bw))
else Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
interval Integer
mask Integer
rl (Integer
rh Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
rl)
where
mask :: Integer
mask = Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a
(Integer
al, Integer
ah) = NatRepr w -> Domain w -> (Integer, Integer)
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> (Integer, Integer)
sbounds NatRepr w
w Domain w
a
(Integer
bl, Integer
bh) = NatRepr w -> Domain w -> (Integer, Integer)
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> (Integer, Integer)
sbounds NatRepr w
w Domain w
b
(Integer
ql, Integer
qh) = (Integer, Integer) -> ReciprocalRange -> (Integer, Integer)
sdivRange (Integer
al, Integer
ah) (NatRepr w -> Domain w -> ReciprocalRange
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> ReciprocalRange
rbounds NatRepr w
w Domain w
b)
rl :: Integer
rl = if Integer
al Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< Integer
0 then Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min (Integer
blInteger -> Integer -> Integer
forall a. Num a => a -> a -> a
+Integer
1) (-Integer
bhInteger -> Integer -> Integer
forall a. Num a => a -> a -> a
+Integer
1) else Integer
0
rh :: Integer
rh = if Integer
ah Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
> Integer
0 then Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
max (-Integer
blInteger -> Integer -> Integer
forall a. Num a => a -> a -> a
-Integer
1) (Integer
bhInteger -> Integer -> Integer
forall a. Num a => a -> a -> a
-Integer
1) else Integer
0
aw :: Integer
aw = Integer
ah Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
al
bw :: Integer
bw = Integer
bh Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
bl
not :: Domain w -> Domain w
not :: Domain w -> Domain w
not Domain w
a =
case Domain w
a of
BVDAny Integer
_ -> Domain w
a
BVDInterval Integer
mask Integer
al Integer
aw ->
Integer -> Integer -> Integer -> Domain w
forall (w :: Nat). Integer -> Integer -> Integer -> Domain w
BVDInterval Integer
mask (Integer -> Integer
forall a. Bits a => a -> a
complement Integer
ah Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Integer
mask) Integer
aw
where ah :: Integer
ah = Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw
bitbounds :: Domain w -> (Integer, Integer)
bitbounds :: Domain w -> (Integer, Integer)
bitbounds Domain w
a =
case Domain w
a of
BVDAny Integer
mask -> (Integer
0, Integer
mask)
BVDInterval Integer
mask Integer
al Integer
aw
| Integer
al Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
aw Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
> Integer
mask -> (Integer
0, Integer
mask)
| Bool
otherwise -> (Integer
lo, Integer
hi)
where
au :: Integer
au = Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
unknowns Domain w
a
hi :: Integer
hi = Integer
al Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.|. Integer
au
lo :: Integer
lo = Integer
hi Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
`Bits.xor` Integer
au
unknowns :: Domain w -> Integer
unknowns :: Domain w -> Integer
unknowns (BVDAny Integer
mask) = Integer
mask
unknowns (BVDInterval Integer
mask Integer
al Integer
aw) = Integer
mask Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. (Integer -> Integer
fillright (Integer
al Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
`Bits.xor` (Integer
alInteger -> Integer -> Integer
forall a. Num a => a -> a -> a
+Integer
aw)))
bitle :: Integer -> Integer -> Bool
bitle :: Integer -> Integer -> Bool
bitle Integer
x Integer
y = (Integer
x Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.|. Integer
y) Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
y
fillright :: Integer -> Integer
fillright :: Integer -> Integer
fillright = Int -> Integer -> Integer
go Int
1
where
go :: Int -> Integer -> Integer
go :: Int -> Integer -> Integer
go Int
i Integer
x
| Integer
x' Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
x = Integer
x
| Bool
otherwise = Int -> Integer -> Integer
go (Int
2 Int -> Int -> Int
forall a. Num a => a -> a -> a
* Int
i) Integer
x'
where x' :: Integer
x' = Integer
x Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.|. (Integer
x Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` Int
i)
pmember :: NatRepr n -> Domain n -> Integer -> Bool
pmember :: NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n Domain n
a Integer
x = NatRepr n -> Domain n -> Bool
forall (w :: Nat). NatRepr w -> Domain w -> Bool
proper NatRepr n
n Domain n
a Bool -> Bool -> Bool
&& Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x
correct_any :: (1 <= n) => NatRepr n -> Integer -> Property
correct_any :: NatRepr n -> Integer -> Property
correct_any NatRepr n
w Integer
x = Bool -> Property
property (NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
w (NatRepr n -> Domain n
forall (w :: Nat). (1 <= w) => NatRepr w -> Domain w
any NatRepr n
w) Integer
x)
correct_ubounds :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> Property
correct_ubounds :: NatRepr n -> (Domain n, Integer) -> Property
correct_ubounds NatRepr n
n (Domain n
a,Integer
x) = NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n Domain n
a Integer
x' Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Integer
lo Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
<= Integer
x' Bool -> Bool -> Bool
&& Integer
x' Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
<= Integer
hi
where
x' :: Integer
x' = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x
(Integer
lo,Integer
hi) = Domain n -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
ubounds Domain n
a
correct_sbounds :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> Property
correct_sbounds :: NatRepr n -> (Domain n, Integer) -> Property
correct_sbounds NatRepr n
n (Domain n
a,Integer
x) = NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n Domain n
a Integer
x' Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Integer
lo Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
<= Integer
x' Bool -> Bool -> Bool
&& Integer
x' Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
<= Integer
hi
where
x' :: Integer
x' = NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
x
(Integer
lo,Integer
hi) = NatRepr n -> Domain n -> (Integer, Integer)
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> (Integer, Integer)
sbounds NatRepr n
n Domain n
a
correct_singleton :: (1 <= n) => NatRepr n -> Integer -> Integer -> Property
correct_singleton :: NatRepr n -> Integer -> Integer -> Property
correct_singleton NatRepr n
n Integer
x Integer
y = Bool -> Property
property (NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (NatRepr n -> Integer -> Domain n
forall (w :: Nat).
(HasCallStack, 1 <= w) =>
NatRepr w -> Integer -> Domain w
singleton NatRepr n
n Integer
x') Integer
y' Bool -> Bool -> Bool
forall a. Eq a => a -> a -> Bool
== (Integer
x' Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
y'))
where
x' :: Integer
x' = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x
y' :: Integer
y' = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
y
correct_overlap :: Domain n -> Domain n -> Integer -> Property
correct_overlap :: Domain n -> Domain n -> Integer -> Property
correct_overlap Domain n
a Domain n
b Integer
x =
Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Bool -> Bool
&& Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
x Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Domain n -> Bool
forall (w :: Nat). Domain w -> Domain w -> Bool
domainsOverlap Domain n
a Domain n
b
correct_union :: (1 <= n) => NatRepr n -> Domain n -> Domain n -> Integer -> Property
correct_union :: NatRepr n -> Domain n -> Domain n -> Integer -> Property
correct_union NatRepr n
n Domain n
a Domain n
b Integer
x =
(Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Bool -> Bool
|| Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
x) Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (Domain n -> Domain n -> Domain n
forall (w :: Nat). (1 <= w) => Domain w -> Domain w -> Domain w
union Domain n
a Domain n
b) Integer
x
correct_zero_ext :: (1 <= w, w+1 <= u) => NatRepr w -> Domain w -> NatRepr u -> Integer -> Property
correct_zero_ext :: NatRepr w -> Domain w -> NatRepr u -> Integer -> Property
correct_zero_ext NatRepr w
w Domain w
a NatRepr u
u Integer
x = Domain w -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain w
a Integer
x' Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr u -> Domain u -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr u
u (Domain w -> NatRepr u -> Domain u
forall (w :: Nat) (u :: Nat).
(1 <= w, (w + 1) <= u) =>
Domain w -> NatRepr u -> Domain u
zext Domain w
a NatRepr u
u) Integer
x'
where
x' :: Integer
x' = NatRepr w -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr w
w Integer
x
correct_sign_ext :: (1 <= w, w+1 <= u) => NatRepr w -> Domain w -> NatRepr u -> Integer -> Property
correct_sign_ext :: NatRepr w -> Domain w -> NatRepr u -> Integer -> Property
correct_sign_ext NatRepr w
w Domain w
a NatRepr u
u Integer
x = Domain w -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain w
a Integer
x' Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr u -> Domain u -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr u
u (NatRepr w -> Domain w -> NatRepr u -> Domain u
forall (w :: Nat) (u :: Nat).
(1 <= w, (w + 1) <= u) =>
NatRepr w -> Domain w -> NatRepr u -> Domain u
sext NatRepr w
w Domain w
a NatRepr u
u) Integer
x'
where
x' :: Integer
x' = NatRepr w -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr w
w Integer
x
correct_concat :: NatRepr m -> (Domain m,Integer) -> NatRepr n -> (Domain n,Integer) -> Property
correct_concat :: NatRepr m
-> (Domain m, Integer)
-> NatRepr n
-> (Domain n, Integer)
-> Property
correct_concat NatRepr m
m (Domain m
a,Integer
x) NatRepr n
n (Domain n
b,Integer
y) = Domain m -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain m
a Integer
x' Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y' Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr (m + n) -> Domain (m + n) -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember (NatRepr m -> NatRepr n -> NatRepr (m + n)
forall (m :: Nat) (n :: Nat).
NatRepr m -> NatRepr n -> NatRepr (m + n)
addNat NatRepr m
m NatRepr n
n) (NatRepr m -> Domain m -> NatRepr n -> Domain n -> Domain (m + n)
forall (u :: Nat) (v :: Nat).
NatRepr u -> Domain u -> NatRepr v -> Domain v -> Domain (u + v)
concat NatRepr m
m Domain m
a NatRepr n
n Domain n
b) Integer
z
where
x' :: Integer
x' = NatRepr m -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr m
m Integer
x
y' :: Integer
y' = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
y
z :: Integer
z = Integer
x' Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftL` (NatRepr n -> Int
forall (n :: Nat). NatRepr n -> Int
widthVal NatRepr n
n) Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.|. Integer
y'
correct_shrink :: NatRepr i -> NatRepr n -> (Domain (i + n), Integer) -> Property
correct_shrink :: NatRepr i -> NatRepr n -> (Domain (i + n), Integer) -> Property
correct_shrink NatRepr i
i NatRepr n
n (Domain (i + n)
a,Integer
x) = Domain (i + n) -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain (i + n)
a Integer
x' Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (NatRepr i -> Domain (i + n) -> Domain n
forall (i :: Nat) (n :: Nat).
NatRepr i -> Domain (i + n) -> Domain n
shrink NatRepr i
i Domain (i + n)
a) (Integer
x' Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` NatRepr i -> Int
forall (n :: Nat). NatRepr n -> Int
widthVal NatRepr i
i)
where
x' :: Integer
x' = Integer
x Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Domain (i + n) -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain (i + n)
a
correct_trunc :: (n <= w) => NatRepr n -> (Domain w, Integer) -> Property
correct_trunc :: NatRepr n -> (Domain w, Integer) -> Property
correct_trunc NatRepr n
n (Domain w
a,Integer
x) = Domain w -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain w
a Integer
x' Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (NatRepr n -> Domain w -> Domain n
forall (n :: Nat) (w :: Nat).
(n <= w) =>
NatRepr n -> Domain w -> Domain n
trunc NatRepr n
n Domain w
a) (NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x')
where
x' :: Integer
x' = Integer
x Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a
correct_select :: (1 <= n, i + n <= w) =>
NatRepr i -> NatRepr n -> (Domain w, Integer) -> Property
correct_select :: NatRepr i -> NatRepr n -> (Domain w, Integer) -> Property
correct_select NatRepr i
i NatRepr n
n (Domain w
a, Integer
x) = Domain w -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain w
a Integer
x Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (NatRepr i -> NatRepr n -> Domain w -> Domain n
forall (n :: Nat) (i :: Nat) (w :: Nat).
(1 <= n, (i + n) <= w) =>
NatRepr i -> NatRepr n -> Domain w -> Domain n
select NatRepr i
i NatRepr n
n Domain w
a) Integer
y
where
y :: Integer
y = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n ((Integer
x Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.&. Domain w -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain w
a) Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` (NatRepr i -> Int
forall (n :: Nat). NatRepr n -> Int
widthVal NatRepr i
i))
correct_add :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_add :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_add NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (Domain n -> Domain n -> Domain n
forall (w :: Nat). (1 <= w) => Domain w -> Domain w -> Domain w
add Domain n
a Domain n
b) (Integer
x Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Integer
y)
correct_neg :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> Property
correct_neg :: NatRepr n -> (Domain n, Integer) -> Property
correct_neg NatRepr n
n (Domain n
a,Integer
x) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (Domain n -> Domain n
forall (w :: Nat). (1 <= w) => Domain w -> Domain w
negate Domain n
a) (Integer -> Integer
forall a. Num a => a -> a
Prelude.negate Integer
x)
correct_not :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> Property
correct_not :: NatRepr n -> (Domain n, Integer) -> Property
correct_not NatRepr n
n (Domain n
a,Integer
x) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (Domain n -> Domain n
forall (w :: Nat). Domain w -> Domain w
not Domain n
a) (Integer -> Integer
forall a. Bits a => a -> a
complement Integer
x)
correct_mul :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_mul :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_mul NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (Domain n -> Domain n -> Domain n
forall (w :: Nat). (1 <= w) => Domain w -> Domain w -> Domain w
mul Domain n
a Domain n
b) (Integer
x Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
y)
correct_scale :: (1 <= n) => NatRepr n -> Integer -> (Domain n, Integer) -> Property
correct_scale :: NatRepr n -> Integer -> (Domain n, Integer) -> Property
correct_scale NatRepr n
n Integer
k (Domain n
a,Integer
x) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (Integer -> Domain n -> Domain n
forall (w :: Nat). (1 <= w) => Integer -> Domain w -> Domain w
scale Integer
k' Domain n
a) (Integer
k' Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* Integer
x)
where
k' :: Integer
k' = NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
k
correct_scale_eq :: (1 <= n) => NatRepr n -> Integer -> Domain n -> Property
correct_scale_eq :: NatRepr n -> Integer -> Domain n -> Property
correct_scale_eq NatRepr n
n Integer
k Domain n
a = Bool -> Property
property (Bool -> Property) -> Bool -> Property
forall a b. (a -> b) -> a -> b
$ Domain n -> Domain n -> Bool
forall (w :: Nat). Domain w -> Domain w -> Bool
sameDomain (Integer -> Domain n -> Domain n
forall (w :: Nat). (1 <= w) => Integer -> Domain w -> Domain w
scale Integer
k' Domain n
a) (Domain n -> Domain n -> Domain n
forall (w :: Nat). (1 <= w) => Domain w -> Domain w -> Domain w
mul (NatRepr n -> Integer -> Domain n
forall (w :: Nat).
(HasCallStack, 1 <= w) =>
NatRepr w -> Integer -> Domain w
singleton NatRepr n
n Integer
k) Domain n
a)
where
k' :: Integer
k' = NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
k
correct_udiv :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_udiv :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_udiv NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x' Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y' Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Integer
y' Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
/= Integer
0 Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (Domain n -> Domain n -> Domain n
forall (w :: Nat). (1 <= w) => Domain w -> Domain w -> Domain w
udiv Domain n
a Domain n
b) (Integer
x' Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`quot` Integer
y')
where
x' :: Integer
x' = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x
y' :: Integer
y' = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
y
correct_urem :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_urem :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_urem NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x' Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y' Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Integer
y' Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
/= Integer
0 Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (Domain n -> Domain n -> Domain n
forall (w :: Nat). (1 <= w) => Domain w -> Domain w -> Domain w
urem Domain n
a Domain n
b) (Integer
x' Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`rem` Integer
y')
where
x' :: Integer
x' = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x
y' :: Integer
y' = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
y
correct_sdivRange :: (Integer, Integer) -> (Integer, Integer) -> Integer -> Integer -> Property
correct_sdivRange :: (Integer, Integer)
-> (Integer, Integer) -> Integer -> Integer -> Property
correct_sdivRange (Integer, Integer)
a (Integer, Integer)
b Integer
x Integer
y =
(Integer, Integer) -> Integer -> Bool
forall a. Ord a => (a, a) -> a -> Bool
mem (Integer, Integer)
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> (Integer, Integer) -> Integer -> Bool
forall a. Ord a => (a, a) -> a -> Bool
mem (Integer, Integer)
b Integer
y Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Integer
y Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
/= Integer
0 Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> (Integer, Integer) -> Integer -> Bool
forall a. Ord a => (a, a) -> a -> Bool
mem ((Integer, Integer) -> ReciprocalRange -> (Integer, Integer)
sdivRange (Integer, Integer)
a ReciprocalRange
b') (Integer
x Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`quot` Integer
y)
where
b' :: ReciprocalRange
b' = Integer -> Integer -> ReciprocalRange
ReciprocalRange ((Integer, Integer) -> Integer
forall a b. (a, b) -> b
snd (Integer, Integer)
b) ((Integer, Integer) -> Integer
forall a b. (a, b) -> a
fst (Integer, Integer)
b)
mem :: (a, a) -> a -> Bool
mem (a
lo,a
hi) a
v = a
lo a -> a -> Bool
forall a. Ord a => a -> a -> Bool
<= a
v Bool -> Bool -> Bool
&& a
v a -> a -> Bool
forall a. Ord a => a -> a -> Bool
<= a
hi
correct_sdiv :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_sdiv :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_sdiv NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) =
Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Integer
y Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
/= Integer
0 Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (NatRepr n -> Domain n -> Domain n -> Domain n
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> Domain w -> Domain w
sdiv NatRepr n
n Domain n
a Domain n
b) (Integer
x' Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`quot` Integer
y')
where
x' :: Integer
x' = NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
x
y' :: Integer
y' = NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
y
correct_srem :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_srem :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_srem NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) =
Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Integer
y Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
/= Integer
0 Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (NatRepr n -> Domain n -> Domain n -> Domain n
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> Domain w -> Domain w
srem NatRepr n
n Domain n
a Domain n
b) (Integer
x' Integer -> Integer -> Integer
forall a. Integral a => a -> a -> a
`rem` Integer
y')
where
x' :: Integer
x' = NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
x
y' :: Integer
y' = NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
y
correct_shl :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_shl :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_shl NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (NatRepr n -> Domain n -> Domain n -> Domain n
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> Domain w -> Domain w
shl NatRepr n
n Domain n
a Domain n
b) Integer
z
where
z :: Integer
z = (NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x) Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftL` Integer -> Int
forall a. Num a => Integer -> a
fromInteger (Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min (NatRepr n -> Integer
forall (w :: Nat). NatRepr w -> Integer
intValue NatRepr n
n) Integer
y)
correct_lshr :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_lshr :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_lshr NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (NatRepr n -> Domain n -> Domain n -> Domain n
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> Domain w -> Domain w
lshr NatRepr n
n Domain n
a Domain n
b) Integer
z
where
z :: Integer
z = (NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x) Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` Integer -> Int
forall a. Num a => Integer -> a
fromInteger (Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min (NatRepr n -> Integer
forall (w :: Nat). NatRepr w -> Integer
intValue NatRepr n
n) Integer
y)
correct_ashr :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_ashr :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_ashr NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> NatRepr n -> Domain n -> Integer -> Bool
forall (n :: Nat). NatRepr n -> Domain n -> Integer -> Bool
pmember NatRepr n
n (NatRepr n -> Domain n -> Domain n -> Domain n
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> Domain w -> Domain w
ashr NatRepr n
n Domain n
a Domain n
b) Integer
z
where
z :: Integer
z = (NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
x) Integer -> Int -> Integer
forall a. Bits a => a -> Int -> a
`shiftR` Integer -> Int
forall a. Num a => Integer -> a
fromInteger (Integer -> Integer -> Integer
forall a. Ord a => a -> a -> a
min (NatRepr n -> Integer
forall (w :: Nat). NatRepr w -> Integer
intValue NatRepr n
n) Integer
y)
correct_eq :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_eq :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_eq NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) =
Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==>
case Domain n -> Domain n -> Maybe Bool
forall (w :: Nat). Domain w -> Domain w -> Maybe Bool
eq Domain n
a Domain n
b of
Just Bool
True -> NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
y
Just Bool
False -> NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
/= NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
y
Maybe Bool
Nothing -> Bool
True
correct_ult :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_ult :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_ult NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) =
Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==>
case Domain n -> Domain n -> Maybe Bool
forall (w :: Nat). (1 <= w) => Domain w -> Domain w -> Maybe Bool
ult Domain n
a Domain n
b of
Just Bool
True -> NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
y
Just Bool
False -> NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
>= NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
y
Maybe Bool
Nothing -> Bool
True
correct_slt :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_slt :: NatRepr n -> (Domain n, Integer) -> (Domain n, Integer) -> Property
correct_slt NatRepr n
n (Domain n
a,Integer
x) (Domain n
b,Integer
y) =
Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
b Integer
y Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==>
case NatRepr n -> Domain n -> Domain n -> Maybe Bool
forall (w :: Nat).
(1 <= w) =>
NatRepr w -> Domain w -> Domain w -> Maybe Bool
slt NatRepr n
n Domain n
a Domain n
b of
Just Bool
True -> NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
x Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
< NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
y
Just Bool
False -> NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
x Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
>= NatRepr n -> Integer -> Integer
forall (w :: Nat). (1 <= w) => NatRepr w -> Integer -> Integer
toSigned NatRepr n
n Integer
y
Maybe Bool
Nothing -> Bool
True
correct_unknowns :: (1 <= n) => Domain n -> Integer -> Integer -> Property
correct_unknowns :: Domain n -> Integer -> Integer -> Property
correct_unknowns Domain n
a Integer
x Integer
y = Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Property -> Property
forall t. Verifiable t => Bool -> t -> Property
==> Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
y Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> ((Integer
x Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.|. Integer
u) Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== (Integer
y Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.|. Integer
u)) Bool -> Bool -> Bool
&& (Integer
u Integer -> Integer -> Integer
forall a. Bits a => a -> a -> a
.|. Integer
mask Integer -> Integer -> Bool
forall a. Eq a => a -> a -> Bool
== Integer
mask)
where
u :: Integer
u = Domain n -> Integer
forall (w :: Nat). Domain w -> Integer
unknowns Domain n
a
mask :: Integer
mask = Domain n -> Integer
forall (w :: Nat). Domain w -> Integer
bvdMask Domain n
a
correct_bitbounds :: (1 <= n) => NatRepr n -> (Domain n, Integer) -> Property
correct_bitbounds :: NatRepr n -> (Domain n, Integer) -> Property
correct_bitbounds NatRepr n
n (Domain n
a,Integer
x) =
Domain n -> Integer -> Bool
forall (w :: Nat). Domain w -> Integer -> Bool
member Domain n
a Integer
x Bool -> Bool -> Property
forall t. Verifiable t => Bool -> t -> Property
==> (Integer -> Integer -> Bool
bitle Integer
lo Integer
x' Bool -> Bool -> Bool
&& Integer -> Integer -> Bool
bitle Integer
x' Integer
hi Bool -> Bool -> Bool
&& Integer -> Integer -> Bool
bitle Integer
hi (NatRepr n -> Integer
forall (w :: Nat). NatRepr w -> Integer
maxUnsigned NatRepr n
n))
where
x' :: Integer
x' = NatRepr n -> Integer -> Integer
forall (w :: Nat). NatRepr w -> Integer -> Integer
toUnsigned NatRepr n
n Integer
x
(Integer
lo, Integer
hi) = Domain n -> (Integer, Integer)
forall (w :: Nat). Domain w -> (Integer, Integer)
bitbounds Domain n
a