[remove old 'Store' grin operation in favor of the StoreNode and Demote basic ops
John Meacham <john@repetae.net>**20090828041712
 Ignore-this: d690c14ab68a233d4ab6a49920ce2541
] hunk ./src/C/FromGrin2.hs 419
-convertBody (Store  n@NodeC {})  = newNode sptr_t n >>= \(x,y) -> simpleRet y >>= \v -> return (x & v)
-convertBody (Return [n@NodeC {}])  = newNode wptr_t n >>= \(x,y) -> simpleRet y >>= \v -> return (x & v)
+convertBody (BaseOp (StoreNode b)  [n@NodeC {}])  = newNode (bool b wptr_t sptr_t) n >>= \(x,y) -> simpleRet y >>= \v -> return (x & v)
+--convertBody (Return [n@NodeC {}])  = newNode wptr_t n >>= \(x,y) -> simpleRet y >>= \v -> return (x & v)
+--convertBody (Store  n@NodeC {})  = newNode sptr_t n >>= \(x,y) -> simpleRet y >>= \v -> return (x & v)
+--convertBody (Return [n@NodeC {}])  = newNode wptr_t n >>= \(x,y) -> simpleRet y >>= \v -> return (x & v)
hunk ./src/C/FromGrin2.hs 478
-convertBody (BaseOp Promote [v])        | getType v == tyINode = simpleRet =<< f_promote `liftM` convertVal v
-convertBody (Store n@Var {}) | getType n == tyDNode = simpleRet =<< f_demote `liftM` convertVal n
+convertBody (BaseOp Promote [v])       | getType v == tyINode = simpleRet =<< f_promote `liftM` convertVal v
+convertBody (BaseOp Demote [n@Var {}]) | getType n == tyDNode = simpleRet =<< f_demote `liftM` convertVal n
+--convertBody (Store n@Var {}) | getType n == tyDNode = simpleRet =<< f_demote `liftM` convertVal n
hunk ./src/C/FromGrin2.hs 536
-isCompound Store {} = False
+--isCompound Store {} = False
hunk ./src/C/FromGrin2.hs 942
+bool b x y = if b then x else y
hunk ./src/Grin/DeadCode.hs 129
-            g (Store n) = addRule $ doNode n
+            g (BaseOp _ xs) = addRule $ mconcatMap doNode xs
+   --         g (Store n) = addRule $ doNode n
hunk ./src/Grin/DeadCode.hs 143
-            h (p,Store v) = addRule $ mconcat $ [ conditionalRule id  (varValue pv) (doNode v) | pv <- freeVars p]
+            h (p,BaseOp (StoreNode _) [v]) = addRule $ mconcat $ [ conditionalRule id  (varValue pv) (doNode v) | pv <- freeVars p]
+            h (p,BaseOp Demote [v]) = addRule $ mconcat $ [ conditionalRule id  (varValue pv) (doNode v) | pv <- freeVars p]
hunk ./src/Grin/DeadCode.hs 178
-    f (Store (NodeC fn as)) |  Just fn' <- tagToFunction fn = do
+    f (BaseOp (StoreNode False) [NodeC fn as]) |  Just fn' <- tagToFunction fn = do
hunk ./src/Grin/DeadCode.hs 181
-        return $ Store (NodeC fn as)
+        return $ BaseOp (StoreNode False) [NodeC fn as]
hunk ./src/Grin/Devolve.hs 117
-    isAllocing Store {} = True
+    isAllocing (BaseOp StoreNode {} _) = True
hunk ./src/Grin/EvalInline.hs 123
-          | n > 1 = Return $ [NodeC (partialTag fn (n - 1)) (vs ++ a2s)]
+          | n > 1 = dstore (NodeC (partialTag fn (n - 1)) (vs ++ a2s))
hunk ./src/Grin/EvalInline.hs 128
+dstore x = BaseOp (StoreNode True) [x]
+
hunk ./src/Grin/FromE.hs 341
+istore n = BaseOp (StoreNode False) [n]
+dstore n = BaseOp (StoreNode True) [n]
+demote v = BaseOp Demote [v]
+
hunk ./src/Grin/FromE.hs 399
-                        return $ Return [NodeC pt (keepIts as)]
+                        return $ dstore (NodeC pt (keepIts as))
hunk ./src/Grin/FromE.hs 412
+    ce e | Just [z@NodeC {}] <- con e = return (dstore z)
hunk ./src/Grin/FromE.hs 430
-
-
hunk ./src/Grin/FromE.hs 532
-                    return $ e :>>= [v] :-> Store v :>>= [toVal b] :-> Case v (as ++ def)
+                    return $ e :>>= [v] :-> demote v :>>= [toVal b] :-> Case v (as ++ def)
hunk ./src/Grin/FromE.hs 583
-            s = Store (NodeC t (keepIts $ e:as))
+            s = istore (NodeC t (keepIts $ e:as))
hunk ./src/Grin/FromE.hs 599
-    cc e | Just [z] <- con e = return $ if isLifted e then Store z else Return [z]
+    cc e | Just [z] <- con e = return $ BaseOp (StoreNode (not $ isLifted e)) [z] -- if isLifted e then Store z else Return [z]
hunk ./src/Grin/FromE.hs 617
-                    let s = Store (NodeC (partialTag v 0) (keepIts x))
+                    let s = istore (NodeC (partialTag v 0) (keepIts x))
hunk ./src/Grin/FromE.hs 630
-                      else Store (NodeC pt as)
+                      else istore (NodeC pt as)
hunk ./src/Grin/FromE.hs 632
-                    return $ Store (NodeC (tagFlipFunction v) (keepIts as))
+                    return $ istore (NodeC (tagFlipFunction v) (keepIts as))
hunk ./src/Grin/FromE.hs 675
-                    u rs (\y -> Store (NodeC t (map ValUnknown ts)) :>>= [toVal tvr] :-> ss y) (\y -> du :>>= [] :-> dus y)
+                    u rs (\y -> istore (NodeC t (map ValUnknown ts)) :>>= [toVal tvr] :-> ss y) (\y -> du :>>= [] :-> dus y)
hunk ./src/Grin/FromE.hs 681
-    doUpdate vr (Store n@(NodeC t ts)) = (BaseOp Overwrite [vr,n],t,map getType ts)
+    --doUpdate vr (Store n@(NodeC t ts)) = (BaseOp Overwrite [vr,n],t,map getType ts)
+    doUpdate vr (BaseOp StoreNode {} [n@(NodeC t ts)]) = (BaseOp Overwrite [vr,n],t,map getType ts)
hunk ./src/Grin/Grin.hs 166
---    = Demote                -- turn a node into an inode, always okay
-    = Promote               -- turn an inode into a node, the inode _must_ already be a valid node
+    = Demote                -- turn a node into an inode, always okay
+    | Promote               -- turn an inode into a node, the inode _must_ already be a valid node
hunk ./src/Grin/Grin.hs 170
-    | StoreNode !Bool       -- create a new node, Bool is true if it should be an indirect node, the second val is the region
+    | StoreNode !Bool       -- create a new node, Bool is true if it should be an direct node, the second val is the region
hunk ./src/Grin/Grin.hs 194
-    | Store     { expValue :: Val }                                       -- ^ Allocate a new heap node
+--    | Store     { expValue :: Val }                                       -- ^ Allocate a new heap node
hunk ./src/Grin/Grin.hs 503
-    getType (Store v) = case getType v of
-        TyNode -> [TyINode]
-        t -> [TyPtr t]
+--    getType (Store v) = case getType v of
+--        TyNode -> [TyINode]
+--        t -> [TyPtr t]
hunk ./src/Grin/Grin.hs 510
+    getType (BaseOp (StoreNode b) _) = if b then [TyNode] else [TyINode]
hunk ./src/Grin/Grin.hs 576
-    freeVars (Store v) = freeVars v
+--    freeVars (Store v) = freeVars v
hunk ./src/Grin/Grin.hs 593
-    freeVars (Store v) = freeVars v
+--    freeVars (Store v) = freeVars v
hunk ./src/Grin/Grin.hs 633
-    freeVars (Store v) = freeVars v
+--    freeVars (Store v) = freeVars v
hunk ./src/Grin/Lint.hs 134
-    f [Left b] (Store (NodeC n vs)) = hPrintf h "store(%s,%s,%s).\n" (dshow b) (dshow n) (if tagIsWHNF n then "true" else "false")
-    f [Right (Var b _)] (Store (NodeC n vs)) = hPrintf h "store(%s,%s,%s).\n" (dshow b) (dshow n) (if tagIsWHNF n then "true" else "false") >> app n vs
-    f [b] (Store x@Var {}) = do assign "demote" b x
+--    f [Left b] (Store (NodeC n vs)) = hPrintf h "store(%s,%s,%s).\n" (dshow b) (dshow n) (if tagIsWHNF n then "true" else "false")
+--    f [Right (Var b _)] (Store (NodeC n vs)) = hPrintf h "store(%s,%s,%s).\n" (dshow b) (dshow n) (if tagIsWHNF n then "true" else "false") >> app n vs
+--    f [b] (Store x@Var {}) = do assign "demote" b x
hunk ./src/Grin/Lint.hs 274
-    f (Store v) = do
-        t <- tcVal v
-        return (getType (Store v))
+    f e@(BaseOp (StoreNode _) vs) = do
+        [NodeC {}] <- return vs
+        mapM_ tcVal vs
+        return (getType e)
hunk ./src/Grin/Lint.hs 285
+    f (BaseOp Demote [v]) = do
+        TyNode <- tcVal v
+        return [TyINode]
hunk ./src/Grin/NodeAnalyze.hs 11
+import Control.Monad.RWS hiding(join)
hunk ./src/Grin/NodeAnalyze.hs 14
+import IO
hunk ./src/Grin/NodeAnalyze.hs 18
-import Support.FreeVars
-import Support.CanType
-import StringTable.Atom
-import IO
+import Util.UniqueMonad
+import Util.SetLike
hunk ./src/Grin/NodeAnalyze.hs 21
-import Grin.Simplify
hunk ./src/Grin/NodeAnalyze.hs 22
-import Util.UnionSolve
+import Grin.Whiz
+import StringTable.Atom
+import Support.CanType
+import Support.FreeVars
hunk ./src/Grin/NodeAnalyze.hs 27
+import Util.UnionSolve
hunk ./src/Grin/NodeAnalyze.hs 215
-        f (Store w) | TyNode == getType w = do
-            ww <- convertVal w
-            dres [ww]
-        f (Store w) = do
-            ww <- convertVal w
-            dunno [TyPtr (getType w)]
+        f (BaseOp (StoreNode _) w) = do
+            ww <- mapM convertVal w
+            dres ww
+        f (BaseOp Demote w) = do
+            ww <- mapM convertVal w
+            dres ww
+--        f (Store w) = do
+--            ww <- convertVal w
+--            dunno [TyPtr (getType w)]
hunk ./src/Grin/NodeAnalyze.hs 310
+renameUniqueGrin :: Grin -> Grin
+renameUniqueGrin grin = res where
+    (res,()) = evalRWS (execUniqT 1 ans) ( mempty :: Map.Map Atom Atom) (fromList [ x | (x,_) <- grinFuncs grin ] :: Set.Set Atom)
+    ans = do mapGrinFuncsM f grin
+    f (l :-> b) = g b >>= return . (l :->)
+    g a@App  { expFunction = fn } = do
+        m <- lift ask
+        case mlookup fn m of
+            Just fn' -> return a { expFunction = fn' }
+            _ -> return a
+    g a@Call { expValue = Item fn t } = do
+        m <- lift ask
+        case mlookup fn m of
+            Just fn' -> return a { expValue = Item fn' t }
+            _ -> return a
+    g (e@Let { expDefs = defs }) = do
+        (defs',rs) <- liftM unzip $ flip mapM defs $ \d -> do
+            (nn,rs) <- newName (funcDefName d)
+            return (d { funcDefName = nn },rs)
+        local (fromList rs `mappend`) $  mapExpExp g e { expDefs = defs' }
+    g b = mapExpExp g b
+    newName a = do
+        m <- lift get
+        case member a m of
+            False -> do lift $ modify (insert a); return (a,(a,a))
+            True -> do
+            let cfname = do
+                uniq <- newUniq
+                let fname = toAtom $ show a  ++ "-" ++ show uniq
+                if fname `member` (m :: Set.Set Atom) then cfname else return fname
+            nn <- cfname
+            lift $ modify (insert nn)
+            return (nn,(a,nn))
+
+mapGrinFuncsM :: Monad m => (Lam -> m Lam) -> Grin -> m Grin
+mapGrinFuncsM f grin = liftM (`setGrinFunctions` grin) $ mapM  (\x -> do nb <- f (funcDefBody x); return (funcDefName x, nb)) (grinFunctions grin)
hunk ./src/Grin/Noodle.hs 45
-    f (Store v) = return Store `ap` g v
+--    f (Store v) = return Store `ap` g v
hunk ./src/Grin/Noodle.hs 146
+isOmittable (BaseOp Demote _) = True
hunk ./src/Grin/Noodle.hs 148
+isOmittable (BaseOp (StoreNode _) _) = True
hunk ./src/Grin/Noodle.hs 150
-isOmittable (Store x) | getType x /= TyNode = False
-isOmittable (Store {}) = True
+--isOmittable (Store x) | getType x /= TyNode = False
+--isOmittable (Store {}) = True
hunk ./src/Grin/Noodle.hs 188
-        cfunc Store {} = return mempty
+--        cfunc Store {} = return mempty
hunk ./src/Grin/Optimize.hs 182
-        h (Store (NodeC t xs)) | t `member` sset = do
+        h (BaseOp (StoreNode False) [NodeC t xs]) | t `member` sset = do
hunk ./src/Grin/Optimize.hs 185
-            return (App t' xs [TyNode] :>>= [n1] :-> Store n1)
+            return (App t' xs [TyNode] :>>= [n1] :-> demote n1)
hunk ./src/Grin/Optimize.hs 202
-    isSpeculatable Store {} = True
+    isSpeculatable (BaseOp (StoreNode _) _) = True
+    isSpeculatable (BaseOp Promote _) = True
+    isSpeculatable (BaseOp Demote _) = True
hunk ./src/Grin/Optimize.hs 210
+demote x = BaseOp Demote [x]
hunk ./src/Grin/SSimplify.hs 86
+
+dstore x = BaseOp (StoreNode True) [x]
+
+
hunk ./src/Grin/SSimplify.hs 96
-            let ne = if cl == 1 then App fn (gs ++ fs) ty else Return [NodeC (partialTag fn (cl - 1)) (gs ++ fs)]
+            let ne = if cl == 1 then App fn (gs ++ fs) ty else dstore (NodeC (partialTag fn (cl - 1)) (gs ++ fs))
hunk ./src/Grin/SSimplify.hs 105
-                return (unboxModify ur (Case v ls) :>>= vs :-> Return (unboxRet ur vs))
+                return (unboxModify ur (Case v ls) :>>= vs :->  (unboxRet ur vs))
hunk ./src/Grin/SSimplify.hs 130
-    f p (BaseOp Promote [v@Var {}]) =  cse' "Simplify.CSE.fetch" [(gEval v,Return p)]
-    f [p@(Var (V vn) _)] (Return [v@(NodeC t vs)]) | not (isHoly v) = case tagUnfunction t of
-        Nothing -> cse "Simplify.CSE.return-node" [(Return [p],Return [v]),(Store p,Store v)]
-        Just (n,fn) -> local (\s -> s { envPapp = IM.insert vn (t,vs) (envPapp s) }) $ cse' "Simplify.CSE.return-node" [(Return [p],Return [v]),(Store p,Store v)]
-    f [p] (Store v@Var {})  =  cse' "Simplify.CSE.demote" [(BaseOp Promote [p],Return [v]),(gEval p,Return [v])]
-    f [p@(Var (V vn) _)] (Store v@(NodeC t vs)) | not (isHoly v) = case tagIsWHNF t of
-        True -> local (\s -> s { envPush = IM.insert vn (Store v) (envPush s) }) $ cse "Simplify.CSE.store-whnf" [(BaseOp Promote [p],Return [v]),(gEval p,Return [v])]
-        False -> cse' "Simplify.CSE.store" []
+    f p (BaseOp Promote [v@Var {}]) =  cse' "Simplify.CSE.promote" [(gEval v,Return p)]
+    f [p] (BaseOp Demote [v@Var {}]) =  cse' "Simplify.CSE.demote" [(BaseOp Promote [p],Return [v]),(gEval p,Return [v])]
+    f [p@(Var (V vn) _)] (BaseOp (StoreNode isD) [v@(NodeC t vs)]) | not (isHoly v) = case (isD,tagUnfunction t,tagIsWHNF t) of
+        (True,Nothing,_) -> cse "Simplify.CSE.return-node" []
+        (True,Just (n,fn),_) -> local (\s -> s { envPapp = IM.insert vn (t,vs) (envPapp s) }) $ cse' "Simplify.CSE.return-node" []
+        --(False,_,True)  -> local (\s -> s { envPush = IM.insert vn (Store v) (envPush s) }) $ cse "Simplify.CSE.store-whnf" []
+        --(False,_,False) -> cse' "Simplify.CSE.store" []
+        _ -> cse' "Simplify.CSE.store" []
+--    f [p@(Var (V vn) _)] (Return [v@(NodeC t vs)]) | not (isHoly v) = case tagUnfunction t of
+--        Nothing -> cse "Simplify.CSE.return-node" [(Return [p],Return [v]),(Store p,Store v)]
+--        Just (n,fn) -> local (\s -> s { envPapp = IM.insert vn (t,vs) (envPapp s) }) $ cse' "Simplify.CSE.return-node" [(Return [p],Return [v]),(Store p,Store v)]
+--    f [p@(Var (V vn) _)] (Store v@(NodeC t vs)) | not (isHoly v) = case tagIsWHNF t of
+--        True -> local (\s -> s { envPush = IM.insert vn (Store v) (envPush s) }) $ cse "Simplify.CSE.store-whnf" [(BaseOp Promote [p],Return [v]),(gEval p,Return [v])]
+--        False -> cse' "Simplify.CSE.store" []
hunk ./src/Grin/SSimplify.hs 161
-    f (BaseOp Promote [Const x]) rs = do
-        mtick "Grin.Simplify.fetch-const"
-        f (Return [x]) rs
-    f (Store x) rs | valIsNF x = do
-        mtick "Grin.Simplify.store-normalform"
-        f (Return [Const x]) rs
+--    f (BaseOp Promote [Const x]) rs = do
+--        mtick "Grin.Simplify.fetch-const"
+--        f (Return [x]) rs
+--    f (Store x) rs | valIsNF x = do
+--        mtick "Grin.Simplify.store-normalform"
+--        f (Return [Const x]) rs
hunk ./src/Grin/SSimplify.hs 174
-
hunk ./src/Grin/SSimplify.hs 180
-    f a@(Return [NodeC t xs]) ((senv,[NodeC t' ys],b):rs) | t == t' = do
-        mtick "Grin.Simplify.Assign.node-node"
-        dtup xs ys senv b rs
+--    f a@(Return [NodeC t xs]) ((senv,[NodeC t' ys],b):rs) | t == t' = do
+--        mtick "Grin.Simplify.Assign.node-node"
+--        dtup xs ys senv b rs
hunk ./src/Grin/SSimplify.hs 189
-    f (Case v [l]) rs = do
+    f (Case v@Var {} [l]) rs = do
hunk ./src/Grin/SSimplify.hs 283
-data UnboxingResult = UnErr [Ty] | UnTup [Unbox] | UnTail (Set.Set Atom) UnboxingResult
+data UnboxingResult = UnErr [Ty] | UnStore !Bool !Atom [Unbox] | UnReturn [Unbox] | UnTail (Set.Set Atom) UnboxingResult
hunk ./src/Grin/SSimplify.hs 285
-data Unbox = UnNode Atom [Unbox] Ty | UnConst Val | UnUnknown Ty
+data Unbox =  UnConst Val | UnUnknown Ty
hunk ./src/Grin/SSimplify.hs 293
-    getType (UnTup us) = map getType us
+    getType (UnReturn us) = map getType us
+    getType (UnStore b _ _) = [bool b tyDNode tyINode]
hunk ./src/Grin/SSimplify.hs 297
-    getType (UnNode _ _ t) = t
hunk ./src/Grin/SSimplify.hs 300
-unboxRet :: UnboxingResult -> [Val] -> [Val]
+unboxRet :: UnboxingResult -> [Val] -> Exp
hunk ./src/Grin/SSimplify.hs 302
-    f (UnTup xs) vs = let (r,[]) = g xs vs in r
-    f UnErr {} _ = []
-    f _ vs = vs
+    f (UnReturn xs) vs = Return $ let (r,[]) = g xs vs in r
+    f (UnStore b c xs) vs = let (xs',[]) = g xs vs in BaseOp (StoreNode b) [NodeC c xs']
+    f UnErr {} _ = Return []
+    f _ vs = Return vs
hunk ./src/Grin/SSimplify.hs 309
-    g (UnNode a ts _:xs) vs = let (ts',vs') = g ts vs; (r,y) = g xs vs' in (NodeC a ts':r,y)
+ --   g (UnNode a ts _:xs) vs = let (ts',vs') = g ts vs; (r,y) = g xs vs' in (NodeC a ts':r,y)
hunk ./src/Grin/SSimplify.hs 316
-    f (UnTup us) | all isUnUnknown us = Nothing
-    f (UnTup xs) = Just $ concatMap h xs
+    f (UnReturn us) | all isUnUnknown us = Nothing
+    f (UnReturn xs) = Just $ concatMap h xs
+    f (UnStore _ _ ts) = Just $ concatMap h ts
hunk ./src/Grin/SSimplify.hs 321
-    h (UnNode _ ts _) = concatMap h ts
hunk ./src/Grin/SSimplify.hs 326
-    f (UnTup us) | all isUnUnknown us = id
-    f (UnTup xs) = runIdentity . editTail nty (g xs)
+    f (UnReturn us) | all isUnUnknown us = id
+    f (UnReturn xs) = runIdentity . editTail nty (g xs)
+    f (UnStore _ _ us) =runIdentity . editTail nty (z us)
hunk ./src/Grin/SSimplify.hs 332
-    h (UnNode _ us _) (NodeC _ ts) = concat $ zipWith h us ts
+    z xs (BaseOp (StoreNode _) [NodeC _ ts]) = return . Return . concat $ zipWith h xs ts
hunk ./src/Grin/SSimplify.hs 341
-    f (UnTup xs) (UnTup ys) = UnTup (zipWith g xs ys)
-    g (UnNode a1 ubs1 t1) (UnNode a2 ubs2 t2) | a1 == a2 = UnNode a1 (zipWith g ubs1 ubs2) t1
-                                              | otherwise = UnUnknown t1
+    f (UnReturn xs) (UnReturn ys) = UnReturn (zipWith g xs ys)
+    f (UnStore b1 a1 xs1) (UnStore b2 a2 xs2) | a1 == a2 = UnStore b1 a1 (zipWith g xs1 xs2)
+                                              | otherwise = UnReturn [UnUnknown (bool b1 tyDNode tyINode)]
+    f x _ = UnReturn (map UnUnknown (getType x))
+    --g (UnNode a1 ubs1 t1) (UnNode a2 ubs2 t2) | a1 == a2 = UnNode a1 (zipWith g ubs1 ubs2) t1
+    --                                          | otherwise = UnUnknown t1
hunk ./src/Grin/SSimplify.hs 353
-    f (Return rs) = UnTup (map g rs)
+    f (Return rs) = UnReturn (map g rs)
+    f (BaseOp (StoreNode b) [NodeC c xs]) = UnStore b c (map g xs)
hunk ./src/Grin/SSimplify.hs 360
-    f e = UnTup (map UnUnknown $ getType e)
+    f e = UnReturn (map UnUnknown $ getType e)
hunk ./src/Grin/SSimplify.hs 362
-    g (NodeC t xs) = UnNode t (map g xs) tyDNode
+--    g (NodeC t xs) = UnNode t (map g xs) tyDNode
hunk ./src/Grin/SSimplify.hs 386
+bool b x y = if b then x else y
hunk ./src/Grin/Show.hs 76
-prettyExp vl (Store v@Var {}) | getType v == tyDNode = vl <> keyword "demote" <+> prettyVal v
-prettyExp vl (Store v) = vl <> keyword "store" <+> prettyVal v
+--prettyExp vl (Store v@Var {}) | getType v == tyDNode = vl <> keyword "demote" <+> prettyVal v
+--prettyExp vl (Store v) = vl <> keyword "store" <+> prettyVal v
hunk ./src/Grin/Show.hs 93
+prettyExp vl (BaseOp Demote [x]) = vl <> keyword "demote" <+> prettyVal x
+prettyExp vl (BaseOp (StoreNode b) [x]) = vl <> keyword ((if b then "d" else "i") ++ "store") <+> prettyVal x
+prettyExp vl (BaseOp (StoreNode b) [x,y]) = vl <> keyword ((if b then "d" else "i") ++ "store") <+> prettyVal x <> char '@' <> prettyVal y
hunk ./src/Main.hs 73
-import qualified Grin.Simplify