mirror of
https://github.com/github/semantic.git
synced 2024-11-24 08:54:07 +03:00
Rename Store to Heap.
This commit is contained in:
parent
f68da42754
commit
fcf44b5a37
@ -47,10 +47,10 @@ library
|
||||
, Data.Abstract.Environment
|
||||
, Data.Abstract.Evaluatable
|
||||
, Data.Abstract.FreeVariables
|
||||
, Data.Abstract.Heap
|
||||
, Data.Abstract.Live
|
||||
, Data.Abstract.ModuleTable
|
||||
, Data.Abstract.Number
|
||||
, Data.Abstract.Store
|
||||
, Data.Abstract.Type
|
||||
, Data.Abstract.Value
|
||||
-- General datatype definitions & generic algorithms
|
||||
|
@ -6,7 +6,7 @@ module Analysis.Abstract.Caching
|
||||
import Control.Abstract.Analysis
|
||||
import Data.Abstract.Cache
|
||||
import Data.Abstract.Configuration
|
||||
import Data.Abstract.Store
|
||||
import Data.Abstract.Heap
|
||||
import Data.Abstract.Value
|
||||
import Data.Monoid (Alt (..))
|
||||
import Prologue
|
||||
@ -28,21 +28,21 @@ newtype Caching m term value (effects :: [* -> *]) a = Caching (m term value eff
|
||||
|
||||
deriving instance MonadControl term (m term value effects) => MonadControl term (Caching m term value effects)
|
||||
deriving instance MonadEnvironment value (m term value effects) => MonadEnvironment value (Caching m term value effects)
|
||||
deriving instance MonadStore value (m term value effects) => MonadStore value (Caching m term value effects)
|
||||
deriving instance MonadHeap value (m term value effects) => MonadHeap value (Caching m term value effects)
|
||||
deriving instance MonadModuleTable term value (m term value effects) => MonadModuleTable term value (Caching m term value effects)
|
||||
deriving instance MonadEvaluator term value (m term value effects) => MonadEvaluator term value (Caching m term value effects)
|
||||
|
||||
-- | Functionality used to perform caching analysis. This is not exported, and exists primarily for organizational reasons.
|
||||
class MonadEvaluator term value m => MonadCaching term value m where
|
||||
-- | Look up the set of values for a given configuration in the in-cache.
|
||||
consultOracle :: ConfigurationFor term value -> m (Set (value, StoreFor value))
|
||||
consultOracle :: ConfigurationFor term value -> m (Set (value, HeapFor value))
|
||||
-- | Run an action with the given in-cache.
|
||||
withOracle :: CacheFor term value -> m a -> m a
|
||||
|
||||
-- | Look up the set of values for a given configuration in the out-cache.
|
||||
lookupCache :: ConfigurationFor term value -> m (Maybe (Set (value, StoreFor value)))
|
||||
-- | Run an action, caching its result and 'Store' under the given configuration.
|
||||
caching :: ConfigurationFor term value -> Set (value, StoreFor value) -> m value -> m value
|
||||
lookupCache :: ConfigurationFor term value -> m (Maybe (Set (value, HeapFor value)))
|
||||
-- | Run an action, caching its result and 'Heap' under the given configuration.
|
||||
caching :: ConfigurationFor term value -> Set (value, HeapFor value) -> m value -> m value
|
||||
|
||||
-- | Run an action starting from an empty out-cache, and return the out-cache afterwards.
|
||||
isolateCache :: m a -> m (CacheFor term value)
|
||||
@ -62,7 +62,7 @@ instance ( Effectful (m term value)
|
||||
lookupCache configuration = raise (cacheLookup configuration <$> get)
|
||||
caching configuration values action = do
|
||||
raise (modify (cacheSet configuration values))
|
||||
result <- (,) <$> action <*> getStore
|
||||
result <- (,) <$> action <*> getHeap
|
||||
raise (modify (cacheInsert configuration result))
|
||||
pure (fst result)
|
||||
|
||||
@ -98,7 +98,7 @@ instance ( Corecursive term
|
||||
c <- getConfiguration e
|
||||
-- Convergence here is predicated upon an Eq instance, not α-equivalence
|
||||
cache <- converge (\ prevCache -> isolateCache $ do
|
||||
putStore (configurationStore c)
|
||||
putHeap (configurationHeap c)
|
||||
-- We need to reset fresh generation so that this invocation converges.
|
||||
reset 0
|
||||
-- This is subtle: though the calling context supports nondeterminism, we want
|
||||
@ -125,5 +125,5 @@ converge f = loop
|
||||
loop x'
|
||||
|
||||
-- | Nondeterministically write each of a collection of stores & return their associated results.
|
||||
scatter :: (Alternative m, Foldable t, MonadEvaluator term value m) => t (a, Store (LocationFor value) value) -> m a
|
||||
scatter = getAlt . foldMap (\ (value, store') -> Alt (putStore store' *> pure value))
|
||||
scatter :: (Alternative m, Foldable t, MonadEvaluator term value m) => t (a, Heap (LocationFor value) value) -> m a
|
||||
scatter = getAlt . foldMap (\ (value, heap') -> Alt (putHeap heap' *> pure value))
|
||||
|
@ -6,8 +6,8 @@ module Analysis.Abstract.Collecting
|
||||
import Control.Abstract.Analysis
|
||||
import Data.Abstract.Address
|
||||
import Data.Abstract.Configuration
|
||||
import Data.Abstract.Heap
|
||||
import Data.Abstract.Live
|
||||
import Data.Abstract.Store
|
||||
import Data.Abstract.Value
|
||||
import Prologue
|
||||
|
||||
@ -16,7 +16,7 @@ newtype Collecting m term value (effects :: [* -> *]) a = Collecting (m term val
|
||||
|
||||
deriving instance MonadControl term (m term value effects) => MonadControl term (Collecting m term value effects)
|
||||
deriving instance MonadEnvironment value (m term value effects) => MonadEnvironment value (Collecting m term value effects)
|
||||
deriving instance MonadStore value (m term value effects) => MonadStore value (Collecting m term value effects)
|
||||
deriving instance MonadHeap value (m term value effects) => MonadHeap value (Collecting m term value effects)
|
||||
deriving instance MonadModuleTable term value (m term value effects) => MonadModuleTable term value (Collecting m term value effects)
|
||||
|
||||
instance ( Effectful (m term value)
|
||||
@ -24,7 +24,7 @@ instance ( Effectful (m term value)
|
||||
, MonadEvaluator term value (m term value effects)
|
||||
)
|
||||
=> MonadEvaluator term value (Collecting m term value effects) where
|
||||
getConfiguration term = Configuration term <$> askRoots <*> askLocalEnv <*> getStore
|
||||
getConfiguration term = Configuration term <$> askRoots <*> askLocalEnv <*> getHeap
|
||||
|
||||
|
||||
instance ( Effectful (m term value)
|
||||
@ -43,7 +43,7 @@ instance ( Effectful (m term value)
|
||||
analyzeTerm term = do
|
||||
roots <- askRoots
|
||||
v <- liftAnalyze analyzeTerm term
|
||||
modifyStore (gc (roots <> valueRoots v))
|
||||
modifyHeap (gc (roots <> valueRoots v))
|
||||
pure v
|
||||
|
||||
|
||||
@ -56,27 +56,27 @@ askRoots = raise ask
|
||||
-- extraRoots roots = raise . local (<> roots) . lower
|
||||
|
||||
|
||||
-- | Collect any addresses in the store not rooted in or reachable from the given 'Live' set.
|
||||
-- | Collect any addresses in the heap not rooted in or reachable from the given 'Live' set.
|
||||
gc :: ( Ord (LocationFor value)
|
||||
, Foldable (Cell (LocationFor value))
|
||||
, ValueRoots value
|
||||
)
|
||||
=> LiveFor value -- ^ The set of addresses to consider rooted.
|
||||
-> StoreFor value -- ^ A store to collect unreachable addresses within.
|
||||
-> StoreFor value -- ^ A garbage-collected store.
|
||||
gc roots store = storeRestrict store (reachable roots store)
|
||||
=> LiveFor value -- ^ The set of addresses to consider rooted.
|
||||
-> HeapFor value -- ^ A heap to collect unreachable addresses within.
|
||||
-> HeapFor value -- ^ A garbage-collected heap.
|
||||
gc roots heap = heapRestrict heap (reachable roots heap)
|
||||
|
||||
-- | Compute the set of addresses reachable from a given root set in a given store.
|
||||
-- | Compute the set of addresses reachable from a given root set in a given heap.
|
||||
reachable :: ( Ord (LocationFor value)
|
||||
, Foldable (Cell (LocationFor value))
|
||||
, ValueRoots value
|
||||
)
|
||||
=> LiveFor value -- ^ The set of root addresses.
|
||||
-> StoreFor value -- ^ The store to trace addresses through.
|
||||
-> LiveFor value -- ^ The set of addresses reachable from the root set.
|
||||
reachable roots store = go mempty roots
|
||||
=> LiveFor value -- ^ The set of root addresses.
|
||||
-> HeapFor value -- ^ The heap to trace addresses through.
|
||||
-> LiveFor value -- ^ The set of addresses reachable from the root set.
|
||||
reachable roots heap = go mempty roots
|
||||
where go seen set = case liveSplit set of
|
||||
Nothing -> seen
|
||||
Just (a, as) -> go (liveInsert a seen) (case storeLookupAll a store of
|
||||
Just (a, as) -> go (liveInsert a seen) (case heapLookupAll a heap of
|
||||
Just values -> liveDifference (foldr ((<>) . valueRoots) mempty values <> as) seen
|
||||
_ -> seen)
|
||||
|
@ -14,7 +14,7 @@ newtype DeadCode m term value (effects :: [* -> *]) a = DeadCode (m term value e
|
||||
|
||||
deriving instance MonadControl term (m term value effects) => MonadControl term (DeadCode m term value effects)
|
||||
deriving instance MonadEnvironment value (m term value effects) => MonadEnvironment value (DeadCode m term value effects)
|
||||
deriving instance MonadStore value (m term value effects) => MonadStore value (DeadCode m term value effects)
|
||||
deriving instance MonadHeap value (m term value effects) => MonadHeap value (DeadCode m term value effects)
|
||||
deriving instance MonadModuleTable term value (m term value effects) => MonadModuleTable term value (DeadCode m term value effects)
|
||||
deriving instance MonadEvaluator term value (m term value effects) => MonadEvaluator term value (DeadCode m term value effects)
|
||||
|
||||
|
@ -13,7 +13,7 @@ newtype Elaborating m term value (effects :: [* -> *]) a = Elaborating (m term v
|
||||
|
||||
deriving instance MonadControl term (m term value effects) => MonadControl term (Elaborating m term value effects)
|
||||
deriving instance MonadEnvironment value (m term value effects) => MonadEnvironment value (Elaborating m term value effects)
|
||||
deriving instance MonadStore value (m term value effects) => MonadStore value (Elaborating m term value effects)
|
||||
deriving instance MonadHeap value (m term value effects) => MonadHeap value (Elaborating m term value effects)
|
||||
deriving instance MonadModuleTable term value (m term value effects) => MonadModuleTable term value (Elaborating m term value effects)
|
||||
deriving instance MonadEvaluator term value (m term value effects) => MonadEvaluator term value (Elaborating m term value effects)
|
||||
|
||||
|
@ -81,7 +81,7 @@ type EvaluatingEffects term value
|
||||
= '[ Fail -- Failure with an error message
|
||||
, Reader (EnvironmentFor value) -- Local environment (e.g. binding over a closure)
|
||||
, State (EnvironmentFor value) -- Global (imperative) environment
|
||||
, State (StoreFor value) -- The heap
|
||||
, State (HeapFor value) -- The heap
|
||||
, Reader (ModuleTable [term]) -- Cache of unevaluated modules
|
||||
, State (ModuleTable (EnvironmentFor value)) -- Cache of evaluated modules
|
||||
|
||||
@ -110,9 +110,9 @@ instance Members '[State (Map Name (Name, Maybe (Address (LocationFor value) val
|
||||
askLocalEnv = raise ask
|
||||
localEnv f a = raise (local f (lower a))
|
||||
|
||||
instance Member (State (StoreFor value)) effects => MonadStore value (Evaluating term value effects) where
|
||||
getStore = raise get
|
||||
putStore = raise . put
|
||||
instance Member (State (HeapFor value)) effects => MonadHeap value (Evaluating term value effects) where
|
||||
getHeap = raise get
|
||||
putHeap = raise . put
|
||||
|
||||
instance Members '[Reader (ModuleTable [term]), State (ModuleTable (EnvironmentFor value))] effects => MonadModuleTable term value (Evaluating term value effects) where
|
||||
getModuleTable = raise get
|
||||
@ -122,7 +122,7 @@ instance Members '[Reader (ModuleTable [term]), State (ModuleTable (EnvironmentF
|
||||
localModuleTable f a = raise (local f (lower a))
|
||||
|
||||
instance Members (EvaluatingEffects term value) effects => MonadEvaluator term value (Evaluating term value effects) where
|
||||
getConfiguration term = Configuration term mempty <$> askLocalEnv <*> getStore
|
||||
getConfiguration term = Configuration term mempty <$> askLocalEnv <*> getHeap
|
||||
|
||||
instance ( Evaluatable (Base term)
|
||||
, FreeVariables term
|
||||
|
@ -19,7 +19,7 @@ newtype Tracing (trace :: * -> *) m term value (effects :: [* -> *]) a = Tracing
|
||||
|
||||
deriving instance MonadControl term (m term value effects) => MonadControl term (Tracing trace m term value effects)
|
||||
deriving instance MonadEnvironment value (m term value effects) => MonadEnvironment value (Tracing trace m term value effects)
|
||||
deriving instance MonadStore value (m term value effects) => MonadStore value (Tracing trace m term value effects)
|
||||
deriving instance MonadHeap value (m term value effects) => MonadHeap value (Tracing trace m term value effects)
|
||||
deriving instance MonadModuleTable term value (m term value effects) => MonadModuleTable term value (Tracing trace m term value effects)
|
||||
deriving instance MonadEvaluator term value (m term value effects) => MonadEvaluator term value (Tracing trace m term value effects)
|
||||
|
||||
|
@ -7,14 +7,14 @@ import Control.Monad ((<=<))
|
||||
import Data.Abstract.Address
|
||||
import Data.Abstract.Environment
|
||||
import Data.Abstract.FreeVariables
|
||||
import Data.Abstract.Store
|
||||
import Data.Abstract.Heap
|
||||
import Data.Abstract.Value
|
||||
import Data.Foldable (asum, toList)
|
||||
import Data.Semigroup
|
||||
import Data.Semigroup.Reducer
|
||||
import Prelude hiding (fail)
|
||||
|
||||
-- | Defines 'alloc'ation and 'deref'erencing of 'Address'es in a Store.
|
||||
-- | Defines 'alloc'ation and 'deref'erencing of 'Address'es in a Heap.
|
||||
class (Monad m, Ord l, l ~ LocationFor value, Reducer value (Cell l value)) => MonadAddressable l value m where
|
||||
deref :: Address l value -> m value
|
||||
|
||||
@ -25,7 +25,7 @@ class (Monad m, Ord l, l ~ LocationFor value, Reducer value (Cell l value)) => M
|
||||
-- The term is expected to contain one and only one free 'Name', meaning that care should be taken to apply this only to e.g. identifiers.
|
||||
lookupOrAlloc :: ( FreeVariables term
|
||||
, MonadAddressable (LocationFor value) value m
|
||||
, MonadStore value m
|
||||
, MonadHeap value m
|
||||
, Semigroup (CellFor value)
|
||||
)
|
||||
=> term
|
||||
@ -38,7 +38,7 @@ lookupOrAlloc term = let [name] = toList (freeVariables term) in
|
||||
-- | Look up or allocate an address for a 'Name' & assign it a given value, returning the 'Name' paired with the address.
|
||||
lookupOrAlloc' :: ( Semigroup (CellFor value)
|
||||
, MonadAddressable (LocationFor value) value m
|
||||
, MonadStore value m
|
||||
, MonadHeap value m
|
||||
)
|
||||
=> Name
|
||||
-> value
|
||||
@ -52,7 +52,7 @@ lookupOrAlloc' name v env = do
|
||||
|
||||
letrec :: ( MonadAddressable (LocationFor value) value m
|
||||
, MonadEnvironment value m
|
||||
, MonadStore value m
|
||||
, MonadHeap value m
|
||||
)
|
||||
=> Name
|
||||
-> m value
|
||||
@ -67,18 +67,18 @@ letrec name body = do
|
||||
-- Instances
|
||||
|
||||
-- | 'Precise' locations are always 'alloc'ated a fresh 'Address', and 'deref'erence to the 'Latest' value written.
|
||||
instance (MonadFail m, LocationFor value ~ Precise, MonadStore value m) => MonadAddressable Precise value m where
|
||||
deref = maybe uninitializedAddress (pure . unLatest) <=< flip fmap getStore . storeLookup
|
||||
instance (MonadFail m, LocationFor value ~ Precise, MonadHeap value m) => MonadAddressable Precise value m where
|
||||
deref = maybe uninitializedAddress (pure . unLatest) <=< flip fmap getHeap . heapLookup
|
||||
where
|
||||
-- | Fail with a message denoting an uninitialized address (i.e. one which was 'alloc'ated, but never 'assign'ed a value before being 'deref'erenced).
|
||||
uninitializedAddress :: MonadFail m => m a
|
||||
uninitializedAddress = fail "uninitialized address"
|
||||
|
||||
alloc _ = fmap (Address . Precise . storeSize) getStore
|
||||
alloc _ = fmap (Address . Precise . heapSize) getHeap
|
||||
|
||||
|
||||
-- | 'Monovariant' locations 'alloc'ate one 'Address' per unique variable name, and 'deref'erence once per stored value, nondeterministically.
|
||||
instance (Alternative m, LocationFor value ~ Monovariant, MonadStore value m, Ord value) => MonadAddressable Monovariant value m where
|
||||
deref = asum . maybe [] (map pure . toList) <=< flip fmap getStore . storeLookup
|
||||
instance (Alternative m, LocationFor value ~ Monovariant, MonadHeap value m, Ord value) => MonadAddressable Monovariant value m where
|
||||
deref = asum . maybe [] (map pure . toList) <=< flip fmap getHeap . heapLookup
|
||||
|
||||
alloc = pure . Address . Monovariant
|
||||
|
@ -3,8 +3,8 @@ module Control.Abstract.Evaluator
|
||||
( MonadEvaluator(..)
|
||||
, MonadEnvironment(..)
|
||||
, modifyGlobalEnv
|
||||
, MonadStore(..)
|
||||
, modifyStore
|
||||
, MonadHeap(..)
|
||||
, modifyHeap
|
||||
, assign
|
||||
, MonadModuleTable(..)
|
||||
, modifyModuleTable
|
||||
@ -14,8 +14,8 @@ module Control.Abstract.Evaluator
|
||||
import Data.Abstract.Address
|
||||
import Data.Abstract.Configuration
|
||||
import Data.Abstract.FreeVariables
|
||||
import Data.Abstract.Heap
|
||||
import Data.Abstract.ModuleTable
|
||||
import Data.Abstract.Store
|
||||
import Data.Abstract.Value
|
||||
import Data.Semigroup.Reducer
|
||||
import Prelude hiding (fail)
|
||||
@ -31,7 +31,7 @@ class ( MonadControl term m
|
||||
, MonadEnvironment value m
|
||||
, MonadFail m
|
||||
, MonadModuleTable term value m
|
||||
, MonadStore value m
|
||||
, MonadHeap value m
|
||||
)
|
||||
=> MonadEvaluator term value m | m -> term, m -> value where
|
||||
-- | Get the current 'Configuration' with a passed-in term.
|
||||
@ -65,27 +65,27 @@ modifyGlobalEnv f = do
|
||||
|
||||
|
||||
-- | A 'Monad' abstracting a heap of values.
|
||||
class Monad m => MonadStore value m | m -> value where
|
||||
class Monad m => MonadHeap value m | m -> value where
|
||||
-- | Retrieve the heap.
|
||||
getStore :: m (StoreFor value)
|
||||
getHeap :: m (HeapFor value)
|
||||
-- | Set the heap.
|
||||
putStore :: StoreFor value -> m ()
|
||||
putHeap :: HeapFor value -> m ()
|
||||
|
||||
-- | Update the heap.
|
||||
modifyStore :: MonadStore value m => (StoreFor value -> StoreFor value) -> m ()
|
||||
modifyStore f = do
|
||||
s <- getStore
|
||||
putStore $! f s
|
||||
modifyHeap :: MonadHeap value m => (HeapFor value -> HeapFor value) -> m ()
|
||||
modifyHeap f = do
|
||||
s <- getHeap
|
||||
putHeap $! f s
|
||||
|
||||
-- | Write a value to the given 'Address' in the 'Store'.
|
||||
assign :: ( Ord (LocationFor value)
|
||||
, MonadStore value m
|
||||
, MonadHeap value m
|
||||
, Reducer value (CellFor value)
|
||||
)
|
||||
=> Address (LocationFor value) value
|
||||
-> value
|
||||
-> m ()
|
||||
assign address = modifyStore . storeInsert address
|
||||
assign address = modifyHeap . heapInsert address
|
||||
|
||||
|
||||
-- | A 'Monad' abstracting tables of modules available for import.
|
||||
|
@ -199,7 +199,7 @@ instance ( Monad m
|
||||
loop = fix
|
||||
|
||||
-- | Discard the value arguments (if any), constructing a 'Type' instead.
|
||||
instance (Alternative m, MonadEnvironment Type m, MonadFail m, MonadFresh m, MonadStore Type m) => MonadValue Type m where
|
||||
instance (Alternative m, MonadEnvironment Type m, MonadFail m, MonadFresh m, MonadHeap Type m) => MonadValue Type m where
|
||||
abstract names (Subterm _ body) = do
|
||||
(env, tvars) <- foldr (\ name rest -> do
|
||||
a <- alloc name
|
||||
|
@ -3,30 +3,30 @@ module Data.Abstract.Cache where
|
||||
|
||||
import Data.Abstract.Address
|
||||
import Data.Abstract.Configuration
|
||||
import Data.Abstract.Store
|
||||
import Data.Abstract.Heap
|
||||
import Data.Map.Monoidal as Monoidal
|
||||
import Prologue
|
||||
|
||||
-- | A map of 'Configuration's to 'Set's of resulting values & 'Store's.
|
||||
newtype Cache l t v = Cache { unCache :: Monoidal.Map (Configuration l t v) (Set (v, Store l v)) }
|
||||
-- | A map of 'Configuration's to 'Set's of resulting values & 'Heap's.
|
||||
newtype Cache l t v = Cache { unCache :: Monoidal.Map (Configuration l t v) (Set (v, Heap l v)) }
|
||||
|
||||
deriving instance (Eq l, Eq t, Eq v, Eq (Cell l v)) => Eq (Cache l t v)
|
||||
deriving instance (Ord l, Ord t, Ord v, Ord (Cell l v)) => Ord (Cache l t v)
|
||||
deriving instance (Show l, Show t, Show v, Show (Cell l v)) => Show (Cache l t v)
|
||||
deriving instance (Ord l, Ord t, Ord v, Ord (Cell l v)) => Semigroup (Cache l t v)
|
||||
deriving instance (Ord l, Ord t, Ord v, Ord (Cell l v)) => Monoid (Cache l t v)
|
||||
deriving instance (Ord l, Ord t, Ord v, Ord (Cell l v)) => Reducer (Configuration l t v, (v, Store l v)) (Cache l t v)
|
||||
deriving instance (Ord l, Ord t, Ord v, Ord (Cell l v)) => Reducer (Configuration l t v, (v, Heap l v)) (Cache l t v)
|
||||
|
||||
-- | Look up the resulting value & 'Store' for a given 'Configuration'.
|
||||
cacheLookup :: (Ord l, Ord t, Ord v, Ord (Cell l v)) => Configuration l t v -> Cache l t v -> Maybe (Set (v, Store l v))
|
||||
-- | Look up the resulting value & 'Heap' for a given 'Configuration'.
|
||||
cacheLookup :: (Ord l, Ord t, Ord v, Ord (Cell l v)) => Configuration l t v -> Cache l t v -> Maybe (Set (v, Heap l v))
|
||||
cacheLookup key = Monoidal.lookup key . unCache
|
||||
|
||||
-- | Set the resulting value & 'Store' for a given 'Configuration', overwriting any previous entry.
|
||||
cacheSet :: (Ord l, Ord t, Ord v, Ord (Cell l v)) => Configuration l t v -> Set (v, Store l v) -> Cache l t v -> Cache l t v
|
||||
-- | Set the resulting value & 'Heap' for a given 'Configuration', overwriting any previous entry.
|
||||
cacheSet :: (Ord l, Ord t, Ord v, Ord (Cell l v)) => Configuration l t v -> Set (v, Heap l v) -> Cache l t v -> Cache l t v
|
||||
cacheSet key value = Cache . Monoidal.insert key value . unCache
|
||||
|
||||
-- | Insert the resulting value & 'Store' for a given 'Configuration', appending onto any previous entry.
|
||||
cacheInsert :: (Ord l, Ord t, Ord v, Ord (Cell l v)) => Configuration l t v -> (v, Store l v) -> Cache l t v -> Cache l t v
|
||||
-- | Insert the resulting value & 'Heap' for a given 'Configuration', appending onto any previous entry.
|
||||
cacheInsert :: (Ord l, Ord t, Ord v, Ord (Cell l v)) => Configuration l t v -> (v, Heap l v) -> Cache l t v -> Cache l t v
|
||||
cacheInsert = curry cons
|
||||
|
||||
|
||||
@ -40,7 +40,7 @@ instance (Show l, Show t, Show1 (Cell l)) => Show1 (Cache l t) where
|
||||
liftShowsPrec spV slV d = showsUnaryWith (liftShowsPrec2 spKey slKey (liftShowsPrec spPair slPair) (liftShowList spPair slPair)) "Cache" d . unCache
|
||||
where spKey = liftShowsPrec spV slV
|
||||
slKey = liftShowList spV slV
|
||||
spPair = liftShowsPrec2 spV slV spStore slStore
|
||||
slPair = liftShowList2 spV slV spStore slStore
|
||||
spStore = liftShowsPrec spV slV
|
||||
slStore = liftShowList spV slV
|
||||
spPair = liftShowsPrec2 spV slV spHeap slHeap
|
||||
slPair = liftShowList2 spV slV spHeap slHeap
|
||||
spHeap = liftShowsPrec spV slV
|
||||
slHeap = liftShowList spV slV
|
||||
|
@ -3,8 +3,8 @@ module Data.Abstract.Configuration where
|
||||
|
||||
import Data.Abstract.Address
|
||||
import Data.Abstract.Environment
|
||||
import Data.Abstract.Heap
|
||||
import Data.Abstract.Live
|
||||
import Data.Abstract.Store
|
||||
import Data.Abstract.Value
|
||||
import Prologue
|
||||
|
||||
@ -17,7 +17,7 @@ data Configuration l t v
|
||||
{ configurationTerm :: t -- ^ The “instruction,” i.e. the current term to evaluate.
|
||||
, configurationRoots :: Live l v -- ^ The set of rooted addresses.
|
||||
, configurationEnvironment :: Environment l v -- ^ The environment binding any free variables in 'configurationTerm'.
|
||||
, configurationStore :: Store l v -- ^ The store of values.
|
||||
, configurationHeap :: Heap l v -- ^ The heap of values.
|
||||
}
|
||||
deriving (Generic1)
|
||||
|
||||
|
45
src/Data/Abstract/Heap.hs
Normal file
45
src/Data/Abstract/Heap.hs
Normal file
@ -0,0 +1,45 @@
|
||||
{-# LANGUAGE GeneralizedNewtypeDeriving, MultiParamTypeClasses, StandaloneDeriving, UndecidableInstances #-}
|
||||
module Data.Abstract.Heap where
|
||||
|
||||
import Data.Abstract.Address
|
||||
import Data.Abstract.Live
|
||||
import qualified Data.Map.Monoidal as Monoidal
|
||||
import Data.Semigroup.Reducer
|
||||
import Prologue
|
||||
|
||||
-- | A map of addresses onto cells holding their values.
|
||||
newtype Heap l a = Heap { unStore :: Monoidal.Map l (Cell l a) }
|
||||
deriving (Generic1)
|
||||
|
||||
deriving instance (Eq l, Eq (Cell l a)) => Eq (Heap l a)
|
||||
deriving instance (Ord l, Ord (Cell l a)) => Ord (Heap l a)
|
||||
deriving instance (Show l, Show (Cell l a)) => Show (Heap l a)
|
||||
instance (Eq l, Eq1 (Cell l)) => Eq1 (Heap l) where liftEq = genericLiftEq
|
||||
instance (Ord l, Ord1 (Cell l)) => Ord1 (Heap l) where liftCompare = genericLiftCompare
|
||||
instance (Show l, Show1 (Cell l)) => Show1 (Heap l) where liftShowsPrec = genericLiftShowsPrec
|
||||
deriving instance Foldable (Cell l) => Foldable (Heap l)
|
||||
deriving instance Functor (Cell l) => Functor (Heap l)
|
||||
deriving instance Traversable (Cell l) => Traversable (Heap l)
|
||||
deriving instance (Ord l, Semigroup (Cell l a)) => Semigroup (Heap l a)
|
||||
deriving instance (Ord l, Semigroup (Cell l a)) => Monoid (Heap l a)
|
||||
deriving instance (Ord l, Reducer a (Cell l a)) => Reducer (l, a) (Heap l a)
|
||||
|
||||
-- | Look up the cell of values for an 'Address' in a 'Heap', if any.
|
||||
heapLookup :: Ord l => Address l a -> Heap l a -> Maybe (Cell l a)
|
||||
heapLookup (Address address) = Monoidal.lookup address . unStore
|
||||
|
||||
-- | Look up the list of values stored for a given address, if any.
|
||||
heapLookupAll :: (Ord l, Foldable (Cell l)) => Address l a -> Heap l a -> Maybe [a]
|
||||
heapLookupAll address = fmap toList . heapLookup address
|
||||
|
||||
-- | Append a value onto the cell for a given address, inserting a new cell if none existed.
|
||||
heapInsert :: (Ord l, Reducer a (Cell l a)) => Address l a -> a -> Heap l a -> Heap l a
|
||||
heapInsert (Address address) value = flip snoc (address, value)
|
||||
|
||||
-- | The number of addresses extant in a 'Heap'.
|
||||
heapSize :: Heap l a -> Int
|
||||
heapSize = Monoidal.size . unStore
|
||||
|
||||
-- | Restrict a 'Heap' to only those 'Address'es in the given 'Live' set (in essence garbage collecting the rest).
|
||||
heapRestrict :: Ord l => Heap l a -> Live l a -> Heap l a
|
||||
heapRestrict (Heap m) roots = Heap (Monoidal.filterWithKey (\ address _ -> Address address `liveMember` roots) m)
|
@ -1,45 +0,0 @@
|
||||
{-# LANGUAGE GeneralizedNewtypeDeriving, MultiParamTypeClasses, StandaloneDeriving, UndecidableInstances #-}
|
||||
module Data.Abstract.Store where
|
||||
|
||||
import Data.Abstract.Address
|
||||
import Data.Abstract.Live
|
||||
import qualified Data.Map.Monoidal as Monoidal
|
||||
import Data.Semigroup.Reducer
|
||||
import Prologue
|
||||
|
||||
-- | A map of addresses onto cells holding their values.
|
||||
newtype Store l a = Store { unStore :: Monoidal.Map l (Cell l a) }
|
||||
deriving (Generic1)
|
||||
|
||||
deriving instance (Eq l, Eq (Cell l a)) => Eq (Store l a)
|
||||
deriving instance (Ord l, Ord (Cell l a)) => Ord (Store l a)
|
||||
deriving instance (Show l, Show (Cell l a)) => Show (Store l a)
|
||||
instance (Eq l, Eq1 (Cell l)) => Eq1 (Store l) where liftEq = genericLiftEq
|
||||
instance (Ord l, Ord1 (Cell l)) => Ord1 (Store l) where liftCompare = genericLiftCompare
|
||||
instance (Show l, Show1 (Cell l)) => Show1 (Store l) where liftShowsPrec = genericLiftShowsPrec
|
||||
deriving instance Foldable (Cell l) => Foldable (Store l)
|
||||
deriving instance Functor (Cell l) => Functor (Store l)
|
||||
deriving instance Traversable (Cell l) => Traversable (Store l)
|
||||
deriving instance (Ord l, Semigroup (Cell l a)) => Semigroup (Store l a)
|
||||
deriving instance (Ord l, Semigroup (Cell l a)) => Monoid (Store l a)
|
||||
deriving instance (Ord l, Reducer a (Cell l a)) => Reducer (l, a) (Store l a)
|
||||
|
||||
-- | Look up the cell of values for an 'Address' in a 'Store', if any.
|
||||
storeLookup :: Ord l => Address l a -> Store l a -> Maybe (Cell l a)
|
||||
storeLookup (Address address) = Monoidal.lookup address . unStore
|
||||
|
||||
-- | Look up the list of values stored for a given address, if any.
|
||||
storeLookupAll :: (Ord l, Foldable (Cell l)) => Address l a -> Store l a -> Maybe [a]
|
||||
storeLookupAll address = fmap toList . storeLookup address
|
||||
|
||||
-- | Append a value onto the cell for a given address, inserting a new cell if none existed.
|
||||
storeInsert :: (Ord l, Reducer a (Cell l a)) => Address l a -> a -> Store l a -> Store l a
|
||||
storeInsert (Address address) value = flip snoc (address, value)
|
||||
|
||||
-- | The number of addresses extant in a 'Store'.
|
||||
storeSize :: Store l a -> Int
|
||||
storeSize = Monoidal.size . unStore
|
||||
|
||||
-- | Restrict a 'Store' to only those 'Address'es in the given 'Live' set (in essence garbage collecting the rest).
|
||||
storeRestrict :: Ord l => Store l a -> Live l a -> Store l a
|
||||
storeRestrict (Store m) roots = Store (Monoidal.filterWithKey (\ address _ -> Address address `liveMember` roots) m)
|
@ -3,8 +3,8 @@ module Data.Abstract.Value where
|
||||
|
||||
import Data.Abstract.Address
|
||||
import Data.Abstract.Environment
|
||||
import Data.Abstract.Store
|
||||
import Data.Abstract.FreeVariables
|
||||
import Data.Abstract.Heap
|
||||
import Data.Abstract.Live
|
||||
import Data.Abstract.Number
|
||||
import qualified Data.Abstract.Type as Type
|
||||
@ -125,8 +125,8 @@ instance Show1 Tuple where liftShowsPrec = genericLiftShowsPrec
|
||||
-- | The environment for an abstract value type.
|
||||
type EnvironmentFor v = Environment (LocationFor v) v
|
||||
|
||||
-- | The store for an abstract value type.
|
||||
type StoreFor v = Store (LocationFor v) v
|
||||
-- | The 'Heap' for an abstract value type.
|
||||
type HeapFor value = Heap (LocationFor value) value
|
||||
|
||||
-- | The cell for an abstract value type.
|
||||
type CellFor value = Cell (LocationFor value) value
|
||||
|
@ -12,8 +12,8 @@ module SpecHelpers (
|
||||
import Data.Abstract.Address as X
|
||||
import Data.Abstract.Environment as X
|
||||
import Data.Abstract.FreeVariables as X
|
||||
import Data.Abstract.Heap as X
|
||||
import Data.Abstract.ModuleTable as X
|
||||
import Data.Abstract.Store as X
|
||||
import Data.Blob as X
|
||||
import Data.Functor.Listable as X
|
||||
import Data.Language as X
|
||||
|
Loading…
Reference in New Issue
Block a user