Skip to content

Commit f3ee6c0

Browse files
authored
Revert "Symbolic rules for SET.in (#2073)" (#2117)
This reverts commit 1ced2ee. The symbolic rules applied to the negative case, but not the positive case. We need to keep the duality between negative and positive cases so that the SMT solver can reason about them. (The SMT solver has no knowledge of SET.)
1 parent 14e6cfb commit f3ee6c0

File tree

5 files changed

+97
-336
lines changed

5 files changed

+97
-336
lines changed

kore/src/Kore/Builtin/Map.hs

Lines changed: 93 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@ import Control.Error
3636
, runMaybeT
3737
)
3838
import qualified Control.Monad as Monad
39+
import qualified Data.Foldable as Foldable
3940
import qualified Data.HashMap.Strict as HashMap
4041
import Data.Map.Strict
4142
( Map
@@ -63,21 +64,25 @@ import qualified Kore.Builtin.Builtin as Builtin
6364
import qualified Kore.Builtin.Int as Int
6465
import qualified Kore.Builtin.List as Builtin.List
6566
import qualified Kore.Builtin.Map.Map as Map
66-
import qualified Kore.Builtin.Set as Set
67+
import qualified Kore.Builtin.Set as Builtin.Set
6768
import qualified Kore.Domain.Builtin as Domain
6869
import Kore.IndexedModule.MetadataTools
6970
( SmtMetadataTools
7071
)
7172
import qualified Kore.Internal.Condition as Condition
73+
import qualified Kore.Internal.OrPattern as OrPattern
7274
import Kore.Internal.Pattern
73-
( Pattern
75+
( Condition
76+
, Pattern
7477
)
7578
import qualified Kore.Internal.Pattern as Pattern
7679
import Kore.Internal.Predicate
7780
( makeCeilPredicate
7881
)
82+
import qualified Kore.Internal.SideCondition as SideCondition
7983
import Kore.Internal.Symbol
80-
( symbolHook
84+
( Symbol (..)
85+
, symbolHook
8186
)
8287
import Kore.Internal.TermLike
8388
( pattern App_
@@ -89,6 +94,7 @@ import qualified Kore.Internal.TermLike as TermLike
8994
import Kore.Sort
9095
( Sort
9196
)
97+
import qualified Kore.Sort as Sort
9298
import Kore.Step.Simplification.NotSimplifier
9399
import Kore.Step.Simplification.Simplify as Simplifier
94100
import Kore.Syntax.Sentence
@@ -97,6 +103,7 @@ import Kore.Syntax.Sentence
97103
import Kore.Unification.Unify
98104
( MonadUnify
99105
)
106+
import qualified Kore.Unification.Unify as Unify
100107
import qualified Kore.Unification.Unify as Monad.Unify
101108
import Kore.Variables.Fresh
102109

@@ -186,7 +193,7 @@ symbolVerifiers =
186193
, Builtin.verifySymbol Bool.assertSort [acceptAnySort, assertSort]
187194
)
188195
, ( Map.keysKey
189-
, Builtin.verifySymbol Set.assertSort [assertSort]
196+
, Builtin.verifySymbol Builtin.Set.assertSort [assertSort]
190197
)
191198
, ( Map.keys_listKey
192199
, Builtin.verifySymbol Builtin.List.assertSort [assertSort]
@@ -195,7 +202,7 @@ symbolVerifiers =
195202
, Builtin.verifySymbol assertSort [assertSort, acceptAnySort]
196203
)
197204
, ( Map.removeAllKey
198-
, Builtin.verifySymbol assertSort [assertSort, Set.assertSort]
205+
, Builtin.verifySymbol assertSort [assertSort, Builtin.Set.assertSort]
199206
)
200207
, ( Map.sizeKey
201208
, Builtin.verifySymbol Int.assertSort [assertSort]
@@ -384,7 +391,7 @@ evalKeys :: Builtin.Function
384391
evalKeys resultSort [_map] = do
385392
_map <- expectConcreteBuiltinMap Map.keysKey _map
386393
fmap (const Domain.SetValue) _map
387-
& Set.returnConcreteSet resultSort
394+
& Builtin.Set.returnConcreteSet resultSort
388395
evalKeys _ _ = Builtin.wrongArity Map.keysKey
389396

390397
evalKeysList :: Builtin.Function
@@ -420,7 +427,7 @@ evalRemoveAll resultSort [_map, _set] = do
420427
bothConcrete = do
421428
_map <- expectConcreteBuiltinMap Map.removeAllKey _map
422429
_set <-
423-
Set.expectConcreteBuiltinSet
430+
Builtin.Set.expectConcreteBuiltinSet
424431
Map.removeAllKey
425432
_set
426433
Map.difference _map _set
@@ -568,26 +575,30 @@ unifyEquals unifyEqualsChildren first second = do
568575
:: Ac.NormalizedOrBottom Domain.NormalizedMap variable
569576
normalizedOrBottom = Ac.toNormalized patt
570577

571-
newtype InKeys term = InKeys { getInKeys :: Set.InKeys term }
578+
data InKeys term =
579+
InKeys
580+
{ symbol :: !Symbol
581+
, keyTerm, mapTerm :: !term
582+
}
572583

573584
instance
574585
InternalVariable variable
575586
=> Injection (TermLike variable) (InKeys (TermLike variable))
576587
where
577-
inject ( InKeys Set.InKeys { symbol, keyTerm, mapTerm } ) =
588+
inject InKeys { symbol, keyTerm, mapTerm } =
578589
TermLike.mkApplySymbol symbol [keyTerm, mapTerm]
579590

580591
retract (App_ symbol [keyTerm, mapTerm]) = do
581592
hook2 <- (getHook . symbolHook) symbol
582593
Monad.guard (hook2 == Map.in_keysKey)
583-
return $ InKeys Set.InKeys { symbol, keyTerm, mapTerm }
594+
return InKeys { symbol, keyTerm, mapTerm }
584595
retract _ = empty
585596

586597
matchInKeys
587598
:: InternalVariable variable
588599
=> TermLike variable
589-
-> Maybe (Set.InKeys (TermLike variable))
590-
matchInKeys = fmap getInKeys . retract
600+
-> Maybe (InKeys (TermLike variable))
601+
matchInKeys = retract
591602

592603
unifyNotInKeys
593604
:: forall variable unifier
@@ -598,8 +609,73 @@ unifyNotInKeys
598609
-> TermLike variable
599610
-> TermLike variable
600611
-> MaybeT unifier (Pattern variable)
601-
unifyNotInKeys =
602-
Set.unifyNotInKeys
603-
(Ac.toNormalized @Domain.NormalizedMap)
604-
matchInKeys
605-
(inject . InKeys)
612+
unifyNotInKeys unifyChildren (NotSimplifier notSimplifier) a b =
613+
worker a b <|> worker b a
614+
where
615+
normalizedOrBottom
616+
:: TermLike variable
617+
-> Ac.NormalizedOrBottom Domain.NormalizedMap variable
618+
normalizedOrBottom = Ac.toNormalized
619+
620+
defineTerm :: TermLike variable -> MaybeT unifier (Condition variable)
621+
defineTerm termLike =
622+
makeEvaluateTermCeil SideCondition.topTODO Sort.predicateSort termLike
623+
>>= Unify.scatter
624+
& lift
625+
626+
eraseTerm =
627+
Pattern.fromCondition_ . Pattern.withoutTerm
628+
629+
unifyAndNegate t1 t2 = do
630+
-- Erasing the unified term is valid here because
631+
-- the terms are all wrapped in \ceil below.
632+
unificationSolutions <-
633+
fmap eraseTerm
634+
<$> Unify.gather (unifyChildren t1 t2)
635+
notSimplifier
636+
SideCondition.top
637+
(OrPattern.fromPatterns unificationSolutions)
638+
>>= Unify.scatter
639+
640+
collectConditions terms =
641+
Foldable.fold terms
642+
& Pattern.fromCondition_
643+
644+
worker
645+
:: TermLike variable
646+
-> TermLike variable
647+
-> MaybeT unifier (Pattern variable)
648+
worker termLike1 termLike2
649+
| Just boolValue <- Bool.matchBool termLike1
650+
, not boolValue
651+
, Just inKeys@InKeys { keyTerm, mapTerm } <- matchInKeys termLike2
652+
, Ac.Normalized normalizedMap <- normalizedOrBottom mapTerm
653+
= do
654+
let symbolicKeys = Domain.getSymbolicKeysOfAc normalizedMap
655+
concreteKeys =
656+
TermLike.fromConcrete
657+
<$> Domain.getConcreteKeysOfAc normalizedMap
658+
mapKeys = symbolicKeys <> concreteKeys
659+
opaqueElements = Domain.opaque . Domain.unwrapAc $ normalizedMap
660+
if null mapKeys && null opaqueElements then
661+
return Pattern.top
662+
else do
663+
Monad.guard (not (null mapKeys) || (length opaqueElements > 1))
664+
-- Concrete keys are constructor-like, therefore they are defined
665+
TermLike.assertConstructorLikeKeys concreteKeys $ return ()
666+
definedKey <- defineTerm keyTerm
667+
definedMap <- defineTerm mapTerm
668+
keyConditions <- lift $ traverse (unifyAndNegate keyTerm) mapKeys
669+
670+
let keyInKeysOpaque =
671+
(\term -> inject @(TermLike _) inKeys { mapTerm = term })
672+
<$> opaqueElements
673+
674+
opaqueConditions <-
675+
lift $ traverse (unifyChildren termLike1) keyInKeysOpaque
676+
let conditions =
677+
fmap Pattern.withoutTerm (keyConditions <> opaqueConditions)
678+
<> [definedKey, definedMap]
679+
return $ collectConditions conditions
680+
681+
worker _ _ = empty

0 commit comments

Comments
 (0)