diff --git a/src/Juvix/Compiler/Asm/Translation/FromTree.hs b/src/Juvix/Compiler/Asm/Translation/FromTree.hs index 65046e645e..45635e1f01 100644 --- a/src/Juvix/Compiler/Asm/Translation/FromTree.hs +++ b/src/Juvix/Compiler/Asm/Translation/FromTree.hs @@ -71,18 +71,18 @@ genCode fi = snocReturn isTail $ DL.snoc (go False _nodeUnopArg) (genUnOp _nodeUnopOpcode) - goConstant :: Bool -> Tree.Constant -> Code' - goConstant isTail c = + goConstant :: Bool -> Tree.NodeConstant -> Code' + goConstant isTail Tree.NodeConstant {..} = snocReturn isTail $ DL.singleton $ mkInstr $ - Push (Constant c) + Push (Constant _nodeConstant) - goMemRef :: Bool -> Tree.MemRef -> Code' - goMemRef isTail ref = + goMemRef :: Bool -> Tree.NodeMemRef -> Code' + goMemRef isTail Tree.NodeMemRef {..} = snocReturn isTail $ DL.singleton $ - mkInstr (Push (Ref ref)) + mkInstr (Push (Ref _nodeMemRef)) goAllocConstr :: Bool -> Tree.NodeAllocConstr -> Code' goAllocConstr isTail Tree.NodeAllocConstr {..} = @@ -212,7 +212,7 @@ genCode fi = ( Save CmdSave { _cmdSaveInfo = emptyInfo, - _cmdSaveName = _nodeSaveTempVarInfo ^. Tree.tempVarInfoName, + _cmdSaveName = _nodeSaveTempVar ^. Tree.tempVarName, _cmdSaveIsTail = isTail, _cmdSaveCode = DL.toList $ go isTail _nodeSaveBody } diff --git a/src/Juvix/Compiler/Tree/Evaluator.hs b/src/Juvix/Compiler/Tree/Evaluator.hs index 0ca20a32be..4711780fec 100644 --- a/src/Juvix/Compiler/Tree/Evaluator.hs +++ b/src/Juvix/Compiler/Tree/Evaluator.hs @@ -11,13 +11,15 @@ import GHC.Show qualified as S import Juvix.Compiler.Core.Data.BinderList qualified as BL import Juvix.Compiler.Tree.Data.InfoTable import Juvix.Compiler.Tree.Error +import Juvix.Compiler.Tree.Extra.Base import Juvix.Compiler.Tree.Language import Juvix.Compiler.Tree.Language.Value import Juvix.Compiler.Tree.Pretty import Text.Read qualified as T -newtype EvalError = EvalError - { _evalErrorMsg :: Text +data EvalError = EvalError + { _evalErrorLocation :: Maybe Location, + _evalErrorMsg :: Text } makeLenses ''EvalError @@ -53,7 +55,7 @@ hEval hout tab = eval' [] mempty where evalError :: Text -> a evalError msg = - Exception.throw (EvalError (msg <> ": " <> ppTrace tab node)) + Exception.throw (EvalError (getNodeLocation node) msg) goBinop :: NodeBinop -> Value goBinop NodeBinop {..} = @@ -127,16 +129,16 @@ hEval hout tab = eval' [] mempty goTrace :: Value -> Value goTrace v = unsafePerformIO (hPutStrLn hout (printValue v) >> return v) - goConstant :: Constant -> Value - goConstant = \case + goConstant :: NodeConstant -> Value + goConstant NodeConstant {..} = case _nodeConstant of ConstInt i -> ValInteger i ConstBool b -> ValBool b ConstString s -> ValString s ConstUnit -> ValUnit ConstVoid -> ValVoid - goMemRef :: MemRef -> Value - goMemRef = \case + goMemRef :: NodeMemRef -> Value + goMemRef NodeMemRef {..} = case _nodeMemRef of DRef r -> goDirectRef r ConstrRef r -> goField r @@ -266,21 +268,23 @@ hEval hout tab = eval' [] mempty valueToNode :: Value -> Node valueToNode = \case - ValInteger i -> Const $ ConstInt i - ValBool b -> Const $ ConstBool b - ValString s -> Const $ ConstString s - ValUnit -> Const ConstUnit - ValVoid -> Const ConstVoid + ValInteger i -> mkConst $ ConstInt i + ValBool b -> mkConst $ ConstBool b + ValString s -> mkConst $ ConstString s + ValUnit -> mkConst ConstUnit + ValVoid -> mkConst ConstVoid ValConstr Constr {..} -> AllocConstr NodeAllocConstr - { _nodeAllocConstrTag = _constrTag, + { _nodeAllocConstrInfo = mempty, + _nodeAllocConstrTag = _constrTag, _nodeAllocConstrArgs = map valueToNode _constrArgs } ValClosure Closure {..} -> AllocClosure NodeAllocClosure - { _nodeAllocClosureFunSymbol = _closureSymbol, + { _nodeAllocClosureInfo = mempty, + _nodeAllocClosureFunSymbol = _closureSymbol, _nodeAllocClosureArgs = map valueToNode _closureArgs } @@ -298,7 +302,8 @@ hRunIO hin hout infoTable = \case let code = CallClosures NodeCallClosures - { _nodeCallClosuresFun = valueToNode f, + { _nodeCallClosuresInfo = mempty, + _nodeCallClosuresFun = valueToNode f, _nodeCallClosuresArgs = valueToNode x' :| [] } !x'' = hEval hout infoTable code @@ -327,5 +332,5 @@ toTreeError :: EvalError -> TreeError toTreeError EvalError {..} = TreeError { _treeErrorMsg = "evaluation error: " <> _evalErrorMsg, - _treeErrorLoc = Nothing + _treeErrorLoc = _evalErrorLocation } diff --git a/src/Juvix/Compiler/Tree/Extra/Base.hs b/src/Juvix/Compiler/Tree/Extra/Base.hs index 5809e71142..98b38072c5 100644 --- a/src/Juvix/Compiler/Tree/Extra/Base.hs +++ b/src/Juvix/Compiler/Tree/Extra/Base.hs @@ -3,10 +3,34 @@ module Juvix.Compiler.Tree.Extra.Base where import Juvix.Compiler.Tree.Language mkBinop :: BinaryOpcode -> Node -> Node -> Node -mkBinop op arg1 arg2 = Binop (NodeBinop op arg1 arg2) +mkBinop op arg1 arg2 = Binop (NodeBinop mempty op arg1 arg2) mkUnop :: UnaryOpcode -> Node -> Node -mkUnop op arg = Unop (NodeUnop op arg) +mkUnop op arg = Unop (NodeUnop mempty op arg) + +mkConst :: Constant -> Node +mkConst c = Const $ NodeConstant mempty c + +mkMemRef :: MemRef -> Node +mkMemRef r = MemRef $ NodeMemRef mempty r + +getNodeInfo :: Node -> NodeInfo +getNodeInfo = \case + Binop NodeBinop {..} -> _nodeBinopInfo + Unop NodeUnop {..} -> _nodeUnopInfo + Const NodeConstant {..} -> _nodeConstantInfo + MemRef NodeMemRef {..} -> _nodeMemRefInfo + AllocConstr NodeAllocConstr {..} -> _nodeAllocConstrInfo + AllocClosure NodeAllocClosure {..} -> _nodeAllocClosureInfo + ExtendClosure NodeExtendClosure {..} -> _nodeExtendClosureInfo + Call NodeCall {..} -> _nodeCallInfo + CallClosures NodeCallClosures {..} -> _nodeCallClosuresInfo + Branch NodeBranch {..} -> _nodeBranchInfo + Case NodeCase {..} -> _nodeCaseInfo + Save NodeSave {..} -> _nodeSaveInfo + +getNodeLocation :: Node -> Maybe Location +getNodeLocation = (^. nodeInfoLocation) . getNodeInfo {------------------------------------------------------------------------} {- generic Node destruction -} @@ -15,7 +39,7 @@ data NodeChild = NodeChild { -- | immediate child of some node _childNode :: Node, -- | `Just i` if the child introduces a temporary variable - _childTempVarInfo :: Maybe TempVarInfo + _childTempVar :: Maybe TempVar } makeLenses ''NodeChild @@ -38,15 +62,15 @@ noTempVar :: Node -> NodeChild noTempVar n = NodeChild { _childNode = n, - _childTempVarInfo = Nothing + _childTempVar = Nothing } {-# INLINE oneTempVar #-} -oneTempVar :: TempVarInfo -> Node -> NodeChild +oneTempVar :: TempVar -> Node -> NodeChild oneTempVar i n = NodeChild { _childNode = n, - _childTempVarInfo = Just i + _childTempVar = Just i } type Reassemble = [Node] -> Node @@ -101,7 +125,8 @@ destruct = \case NodeBinop { _nodeBinopArg1 = arg1, _nodeBinopArg2 = arg2, - _nodeBinopOpcode + _nodeBinopOpcode, + _nodeBinopInfo } } Unop NodeUnop {..} -> @@ -111,7 +136,8 @@ destruct = \case Unop NodeUnop { _nodeUnopArg = arg, - _nodeUnopOpcode + _nodeUnopOpcode, + _nodeUnopInfo } } Const c -> @@ -131,7 +157,8 @@ destruct = \case AllocConstr NodeAllocConstr { _nodeAllocConstrArgs = args, - _nodeAllocConstrTag + _nodeAllocConstrTag, + _nodeAllocConstrInfo } } AllocClosure NodeAllocClosure {..} -> @@ -141,7 +168,8 @@ destruct = \case AllocClosure NodeAllocClosure { _nodeAllocClosureArgs = args, - _nodeAllocClosureFunSymbol + _nodeAllocClosureFunSymbol, + _nodeAllocClosureInfo } } ExtendClosure NodeExtendClosure {..} -> @@ -151,7 +179,8 @@ destruct = \case ExtendClosure NodeExtendClosure { _nodeExtendClosureArgs = nonEmpty' args, - _nodeExtendClosureFun = arg + _nodeExtendClosureFun = arg, + _nodeExtendClosureInfo } } Call NodeCall {..} -> case _nodeCallType of @@ -162,7 +191,8 @@ destruct = \case Call NodeCall { _nodeCallArgs = args, - _nodeCallType = CallFun sym + _nodeCallType = CallFun sym, + _nodeCallInfo } } CallClosure cl -> @@ -172,7 +202,8 @@ destruct = \case Call NodeCall { _nodeCallArgs = args, - _nodeCallType = CallClosure arg + _nodeCallType = CallClosure arg, + _nodeCallInfo } } CallClosures NodeCallClosures {..} -> @@ -182,7 +213,8 @@ destruct = \case CallClosures NodeCallClosures { _nodeCallClosuresArgs = nonEmpty' args, - _nodeCallClosuresFun = arg + _nodeCallClosuresFun = arg, + _nodeCallClosuresInfo } } Branch NodeBranch {..} -> @@ -193,7 +225,8 @@ destruct = \case NodeBranch { _nodeBranchArg = arg, _nodeBranchTrue = br1, - _nodeBranchFalse = br2 + _nodeBranchFalse = br2, + _nodeBranchInfo } } Case NodeCase {..} -> @@ -207,7 +240,8 @@ destruct = \case { _nodeCaseArg = v', _nodeCaseBranches = mkBranches _nodeCaseBranches bodies', _nodeCaseDefault = Nothing, - _nodeCaseInductive + _nodeCaseInductive, + _nodeCaseInfo } } Just def -> @@ -219,7 +253,8 @@ destruct = \case { _nodeCaseArg = v', _nodeCaseBranches = mkBranches _nodeCaseBranches bodies', _nodeCaseDefault = Just def', - _nodeCaseInductive + _nodeCaseInductive, + _nodeCaseInfo } } where @@ -227,19 +262,20 @@ destruct = \case mkBranchChild :: CaseBranch -> NodeChild mkBranchChild CaseBranch {..} = - (if _caseBranchSave then oneTempVar (TempVarInfo Nothing Nothing) else noTempVar) _caseBranchBody + (if _caseBranchSave then oneTempVar (TempVar Nothing Nothing) else noTempVar) _caseBranchBody mkBranches :: [CaseBranch] -> [Node] -> [CaseBranch] mkBranches = zipWithExact (flip (set caseBranchBody)) Save NodeSave {..} -> NodeDetails - { _nodeChildren = [noTempVar _nodeSaveArg, oneTempVar _nodeSaveTempVarInfo _nodeSaveBody], + { _nodeChildren = [noTempVar _nodeSaveArg, oneTempVar _nodeSaveTempVar _nodeSaveBody], _nodeReassemble = twoChildren $ \arg body -> Save NodeSave { _nodeSaveArg = arg, _nodeSaveBody = body, - _nodeSaveTempVarInfo + _nodeSaveTempVar, + _nodeSaveInfo } } diff --git a/src/Juvix/Compiler/Tree/Extra/Recursors/Base.hs b/src/Juvix/Compiler/Tree/Extra/Recursors/Base.hs index 8d3d0dd745..63f2e0ac7d 100644 --- a/src/Juvix/Compiler/Tree/Extra/Recursors/Base.hs +++ b/src/Juvix/Compiler/Tree/Extra/Recursors/Base.hs @@ -17,14 +17,14 @@ import Juvix.Compiler.Tree.Extra.Base import Juvix.Compiler.Tree.Extra.Recursors.Recur import Juvix.Compiler.Tree.Language -instance IsNodeChild NodeChild TempVarInfo where - gBindersNum = fromEnum . isJust . (^. childTempVarInfo) - gBinders = toList . (^. childTempVarInfo) +instance IsNodeChild NodeChild TempVar where + gBindersNum = fromEnum . isJust . (^. childTempVar) + gBinders = toList . (^. childTempVar) instance IsNodeDetails NodeDetails NodeChild where gChildren = (^. nodeChildren) -instance IsNode Node NodeDetails NodeChild TempVarInfo where +instance IsNode Node NodeDetails NodeChild TempVar where gDestruct = destruct gReassemble = reassembleDetails gChild = (^. childNode) diff --git a/src/Juvix/Compiler/Tree/Language.hs b/src/Juvix/Compiler/Tree/Language.hs index 4461853ca0..f515553d46 100644 --- a/src/Juvix/Compiler/Tree/Language.hs +++ b/src/Juvix/Compiler/Tree/Language.hs @@ -13,9 +13,9 @@ data Node = Binop NodeBinop | Unop NodeUnop | -- | A constant value. - Const Constant + Const NodeConstant | -- | A memory reference. - MemRef MemRef + MemRef NodeMemRef | -- | Allocate constructor data. JVT code: 'alloc[](x1, .., xn)'. AllocConstr NodeAllocConstr | -- | Allocate a closure. JVT code: 'calloc[](x1, .., xn)'. @@ -45,6 +45,11 @@ data Node -- 'save[](x) {}'. Save NodeSave +newtype NodeInfo = NodeInfo + { _nodeInfoLocation :: Maybe Location + } + deriving newtype (Semigroup, Monoid) + data BinaryOpcode = IntAdd | IntSub @@ -74,73 +79,98 @@ data UnaryOpcode OpArgsNum data NodeBinop = NodeBinop - { _nodeBinopOpcode :: BinaryOpcode, + { _nodeBinopInfo :: NodeInfo, + _nodeBinopOpcode :: BinaryOpcode, _nodeBinopArg1 :: Node, _nodeBinopArg2 :: Node } data NodeUnop = NodeUnop - { _nodeUnopOpcode :: UnaryOpcode, + { _nodeUnopInfo :: NodeInfo, + _nodeUnopOpcode :: UnaryOpcode, _nodeUnopArg :: Node } +data NodeConstant = NodeConstant + { _nodeConstantInfo :: NodeInfo, + _nodeConstant :: Constant + } + +data NodeMemRef = NodeMemRef + { _nodeMemRefInfo :: NodeInfo, + _nodeMemRef :: MemRef + } + data NodeAllocConstr = NodeAllocConstr - { _nodeAllocConstrTag :: Tag, + { _nodeAllocConstrInfo :: NodeInfo, + _nodeAllocConstrTag :: Tag, _nodeAllocConstrArgs :: [Node] } data NodeAllocClosure = NodeAllocClosure - { _nodeAllocClosureFunSymbol :: Symbol, + { _nodeAllocClosureInfo :: NodeInfo, + _nodeAllocClosureFunSymbol :: Symbol, _nodeAllocClosureArgs :: [Node] } data NodeExtendClosure = NodeExtendClosure - { _nodeExtendClosureFun :: Node, + { _nodeExtendClosureInfo :: NodeInfo, + _nodeExtendClosureFun :: Node, _nodeExtendClosureArgs :: NonEmpty Node } data NodeCall = NodeCall - { _nodeCallType :: CallType, + { _nodeCallInfo :: NodeInfo, + _nodeCallType :: CallType, _nodeCallArgs :: [Node] } data NodeCallClosures = NodeCallClosures - { _nodeCallClosuresFun :: Node, + { _nodeCallClosuresInfo :: NodeInfo, + _nodeCallClosuresFun :: Node, _nodeCallClosuresArgs :: NonEmpty Node } data NodeBranch = NodeBranch - { _nodeBranchArg :: Node, + { _nodeBranchInfo :: NodeInfo, + _nodeBranchArg :: Node, _nodeBranchTrue :: Node, _nodeBranchFalse :: Node } data NodeCase = NodeCase - { _nodeCaseInductive :: Symbol, + { _nodeCaseInfo :: NodeInfo, + _nodeCaseInductive :: Symbol, _nodeCaseArg :: Node, _nodeCaseBranches :: [CaseBranch], _nodeCaseDefault :: Maybe Node } data CaseBranch = CaseBranch - { _caseBranchTag :: Tag, + { _caseBranchLocation :: Maybe Location, + _caseBranchTag :: Tag, _caseBranchBody :: Node, -- | Indicates whether the evaluated case argument should be pushed onto the -- temporary stack in this branch. _caseBranchSave :: Bool } -data TempVarInfo = TempVarInfo - { _tempVarInfoName :: Maybe Text, - _tempVarInfoLocation :: Maybe Location +data TempVar = TempVar + { _tempVarName :: Maybe Text, + _tempVarLocation :: Maybe Location } data NodeSave = NodeSave - { _nodeSaveTempVarInfo :: TempVarInfo, + { _nodeSaveInfo :: NodeInfo, + _nodeSaveTempVar :: TempVar, _nodeSaveArg :: Node, _nodeSaveBody :: Node } +makeLenses ''NodeBinop +makeLenses ''NodeUnop +makeLenses ''NodeConstant +makeLenses ''NodeMemRef makeLenses ''NodeAllocClosure makeLenses ''NodeExtendClosure makeLenses ''NodeCall @@ -148,5 +178,6 @@ makeLenses ''NodeCallClosures makeLenses ''NodeBranch makeLenses ''NodeCase makeLenses ''NodeSave -makeLenses ''TempVarInfo +makeLenses ''TempVar makeLenses ''CaseBranch +makeLenses ''NodeInfo diff --git a/src/Juvix/Compiler/Tree/Pretty/Base.hs b/src/Juvix/Compiler/Tree/Pretty/Base.hs index 4373273905..2641f43424 100644 --- a/src/Juvix/Compiler/Tree/Pretty/Base.hs +++ b/src/Juvix/Compiler/Tree/Pretty/Base.hs @@ -246,6 +246,12 @@ instance PrettyCode NodeUnop where arg <- ppCode _nodeUnopArg return $ op <> parens arg +instance PrettyCode NodeConstant where + ppCode NodeConstant {..} = ppCode _nodeConstant + +instance PrettyCode NodeMemRef where + ppCode NodeMemRef {..} = ppCode _nodeMemRef + ppCodeArgs :: (Member (Reader Options) r) => [Node] -> Sem r (Doc Ann) ppCodeArgs args = do args' <- mapM ppCode args @@ -323,7 +329,7 @@ instance PrettyCode NodeSave where arg <- ppCode _nodeSaveArg body <- ppCode _nodeSaveBody let name = - case _nodeSaveTempVarInfo ^. tempVarInfoName of + case _nodeSaveTempVar ^. tempVarName of Just n -> brackets (variable (quoteName n)) Nothing -> mempty return $ primitive Str.save <> name <> parens arg <+> braces' body diff --git a/src/Juvix/Compiler/Tree/Transformation/Apply.hs b/src/Juvix/Compiler/Tree/Transformation/Apply.hs index 6a4e6f29c1..f5e8b4e277 100644 --- a/src/Juvix/Compiler/Tree/Transformation/Apply.hs +++ b/src/Juvix/Compiler/Tree/Transformation/Apply.hs @@ -2,6 +2,7 @@ module Juvix.Compiler.Tree.Transformation.Apply where import Data.HashMap.Strict qualified as HashMap import Juvix.Compiler.Tree.Extra.Apply +import Juvix.Compiler.Tree.Extra.Base import Juvix.Compiler.Tree.Extra.Recursors import Juvix.Compiler.Tree.Transformation.Base @@ -26,7 +27,8 @@ computeFunctionApply blts = umap go mkApply cl args = Call NodeCall - { _nodeCallType = CallFun sym, + { _nodeCallInfo = getNodeInfo cl, + _nodeCallType = CallFun sym, _nodeCallArgs = cl : toList args } where diff --git a/src/Juvix/Compiler/Tree/Transformation/TempHeight.hs b/src/Juvix/Compiler/Tree/Transformation/TempHeight.hs index 15fd9d0f7a..c2e53bd129 100644 --- a/src/Juvix/Compiler/Tree/Transformation/TempHeight.hs +++ b/src/Juvix/Compiler/Tree/Transformation/TempHeight.hs @@ -8,17 +8,19 @@ computeFunctionTempHeight = umapN go where go :: Int -> Node -> Node go k = \case - MemRef (DRef (TempRef r)) -> + MemRef (NodeMemRef i (DRef (TempRef r))) -> let r' = set refTempTempHeight (Just k) r - in MemRef $ DRef (TempRef r') - MemRef (ConstrRef field@Field {_fieldRef = TempRef r}) -> + in MemRef $ NodeMemRef i $ DRef (TempRef r') + MemRef (NodeMemRef i (ConstrRef field@Field {_fieldRef = TempRef r})) -> let r' = set refTempTempHeight (Just k) r - in MemRef - ( ConstrRef - field - { _fieldRef = TempRef r' - } - ) + in MemRef $ + NodeMemRef + i + ( ConstrRef + field + { _fieldRef = TempRef r' + } + ) node -> node computeTempHeight :: InfoTable -> InfoTable diff --git a/src/Juvix/Compiler/Tree/Translation/FromAsm.hs b/src/Juvix/Compiler/Tree/Translation/FromAsm.hs index b53f456305..769d7a3f9f 100644 --- a/src/Juvix/Compiler/Tree/Translation/FromAsm.hs +++ b/src/Juvix/Compiler/Tree/Translation/FromAsm.hs @@ -5,6 +5,7 @@ import Juvix.Compiler.Asm.Extra.Base qualified as Asm import Juvix.Compiler.Asm.Language qualified as Asm import Juvix.Compiler.Tree.Data.InfoTable import Juvix.Compiler.Tree.Error +import Juvix.Compiler.Tree.Extra.Base import Juvix.Compiler.Tree.Language import Juvix.Compiler.Tree.Translation.FromAsm.Translator @@ -59,7 +60,8 @@ goFunction infoTab fi = do return $ Binop NodeBinop - { _nodeBinopOpcode = OpSeq, + { _nodeBinopInfo = mempty, + _nodeBinopOpcode = OpSeq, _nodeBinopArg1 = node', _nodeBinopArg2 = node } @@ -86,8 +88,8 @@ goFunction infoTab fi = do Asm.Binop op -> goBinop (translateBinop op) Asm.ValShow -> goUnop OpShow Asm.StrToInt -> goUnop OpStrToInt - Asm.Push (Asm.Constant c) -> return (Const c) - Asm.Push (Asm.Ref r) -> return (MemRef r) + Asm.Push (Asm.Constant c) -> return (mkConst c) + Asm.Push (Asm.Ref r) -> return (mkMemRef r) Asm.Pop -> goPop Asm.Trace -> goTrace Asm.Dump -> unsupported (_cmdInstrInfo ^. Asm.commandInfoLocation) @@ -111,7 +113,8 @@ goFunction infoTab fi = do return $ Branch NodeBranch - { _nodeBranchArg = arg, + { _nodeBranchInfo = mempty, + _nodeBranchArg = arg, _nodeBranchTrue = br1, _nodeBranchFalse = br2 } @@ -124,7 +127,8 @@ goFunction infoTab fi = do return $ Case NodeCase - { _nodeCaseInductive = _cmdCaseInductive, + { _nodeCaseInfo = mempty, + _nodeCaseInductive = _cmdCaseInductive, _nodeCaseArg = arg, _nodeCaseBranches = brs, _nodeCaseDefault = def @@ -138,7 +142,8 @@ goFunction infoTab fi = do body <- pushTempStack $ goCodeBlock _cmdSaveCode return $ CaseBranch - { _caseBranchTag, + { _caseBranchLocation = Nothing, + _caseBranchTag, _caseBranchBody = body, _caseBranchSave = True } @@ -146,7 +151,8 @@ goFunction infoTab fi = do body <- goCodeBlock cmds return $ CaseBranch - { _caseBranchTag, + { _caseBranchLocation = Nothing, + _caseBranchTag, _caseBranchBody = body, _caseBranchSave = False } @@ -154,8 +160,9 @@ goFunction infoTab fi = do off <- asks (^. tempSize) return $ CaseBranch - { _caseBranchTag, - _caseBranchBody = MemRef $ DRef $ mkTempRef $ OffsetRef off Nothing, + { _caseBranchLocation = Nothing, + _caseBranchTag, + _caseBranchBody = mkMemRef $ DRef $ mkTempRef $ OffsetRef off Nothing, _caseBranchSave = True } _ -> @@ -183,7 +190,8 @@ goFunction infoTab fi = do return $ Save NodeSave - { _nodeSaveTempVarInfo = TempVarInfo _cmdSaveName (_cmdSaveInfo ^. Asm.commandInfoLocation), + { _nodeSaveInfo = mempty, + _nodeSaveTempVar = TempVar _cmdSaveName (_cmdSaveInfo ^. Asm.commandInfoLocation), _nodeSaveArg = arg, _nodeSaveBody = body } @@ -207,7 +215,8 @@ goFunction infoTab fi = do return $ Binop NodeBinop - { _nodeBinopOpcode = op, + { _nodeBinopInfo = mempty, + _nodeBinopOpcode = op, _nodeBinopArg1 = arg1, _nodeBinopArg2 = arg2 } @@ -218,7 +227,8 @@ goFunction infoTab fi = do return $ Unop NodeUnop - { _nodeUnopArg = arg, + { _nodeUnopInfo = mempty, + _nodeUnopArg = arg, _nodeUnopOpcode = op } @@ -229,7 +239,8 @@ goFunction infoTab fi = do return $ Binop NodeBinop - { _nodeBinopOpcode = OpSeq, + { _nodeBinopInfo = mempty, + _nodeBinopOpcode = OpSeq, _nodeBinopArg1 = arg1, _nodeBinopArg2 = arg2 } @@ -238,20 +249,23 @@ goFunction infoTab fi = do goTrace = do arg <- goCode off <- asks (^. tempSize) - let ref = MemRef $ DRef $ mkTempRef $ OffsetRef off Nothing + let ref = mkMemRef $ DRef $ mkTempRef $ OffsetRef off Nothing return $ Save NodeSave - { _nodeSaveArg = arg, - _nodeSaveTempVarInfo = TempVarInfo Nothing Nothing, + { _nodeSaveInfo = mempty, + _nodeSaveArg = arg, + _nodeSaveTempVar = TempVar Nothing Nothing, _nodeSaveBody = Binop NodeBinop - { _nodeBinopOpcode = OpSeq, + { _nodeBinopInfo = mempty, + _nodeBinopOpcode = OpSeq, _nodeBinopArg1 = Unop NodeUnop - { _nodeUnopOpcode = OpTrace, + { _nodeUnopInfo = mempty, + _nodeUnopOpcode = OpTrace, _nodeUnopArg = ref }, _nodeBinopArg2 = ref @@ -267,7 +281,8 @@ goFunction infoTab fi = do return $ AllocConstr NodeAllocConstr - { _nodeAllocConstrTag = tag, + { _nodeAllocConstrInfo = mempty, + _nodeAllocConstrTag = tag, _nodeAllocConstrArgs = args } where @@ -279,7 +294,8 @@ goFunction infoTab fi = do return $ AllocClosure NodeAllocClosure - { _nodeAllocClosureArgs = args, + { _nodeAllocClosureInfo = mempty, + _nodeAllocClosureArgs = args, _nodeAllocClosureFunSymbol = _allocClosureFunSymbol } @@ -290,7 +306,8 @@ goFunction infoTab fi = do return $ ExtendClosure NodeExtendClosure - { _nodeExtendClosureArgs = nonEmpty' args, + { _nodeExtendClosureInfo = mempty, + _nodeExtendClosureArgs = nonEmpty' args, _nodeExtendClosureFun = cl } @@ -301,7 +318,8 @@ goFunction infoTab fi = do return $ Call NodeCall - { _nodeCallType = CallFun sym, + { _nodeCallInfo = mempty, + _nodeCallType = CallFun sym, _nodeCallArgs = args } Asm.CallClosure -> do @@ -310,7 +328,8 @@ goFunction infoTab fi = do return $ Call NodeCall - { _nodeCallType = CallClosure cl, + { _nodeCallInfo = mempty, + _nodeCallType = CallClosure cl, _nodeCallArgs = args } @@ -321,7 +340,8 @@ goFunction infoTab fi = do return $ CallClosures NodeCallClosures - { _nodeCallClosuresFun = cl, + { _nodeCallClosuresInfo = mempty, + _nodeCallClosuresFun = cl, _nodeCallClosuresArgs = nonEmpty' args } diff --git a/src/Juvix/Compiler/Tree/Translation/FromCore.hs b/src/Juvix/Compiler/Tree/Translation/FromCore.hs index 67148353ab..0903b6f47a 100644 --- a/src/Juvix/Compiler/Tree/Translation/FromCore.hs +++ b/src/Juvix/Compiler/Tree/Translation/FromCore.hs @@ -5,6 +5,7 @@ import Juvix.Compiler.Core.Data.BinderList qualified as BL import Juvix.Compiler.Core.Data.Stripped.InfoTable qualified as Core import Juvix.Compiler.Core.Language.Stripped qualified as Core import Juvix.Compiler.Tree.Data.InfoTable +import Juvix.Compiler.Tree.Extra.Base import Juvix.Compiler.Tree.Extra.Type import Juvix.Compiler.Tree.Language @@ -56,29 +57,31 @@ genCode infoTable fi = goVar :: BinderList MemRef -> Core.Var -> Node goVar refs Core.Var {..} = - MemRef (BL.lookup _varIndex refs) + mkMemRef (BL.lookup _varIndex refs) goIdent :: Core.Ident -> Node goIdent Core.Ident {..} | getArgsNum _identSymbol == 0 = Call $ NodeCall - { _nodeCallType = CallFun _identSymbol, + { _nodeCallInfo = mempty, + _nodeCallType = CallFun _identSymbol, _nodeCallArgs = [] } | otherwise = AllocClosure $ NodeAllocClosure - { _nodeAllocClosureFunSymbol = _identSymbol, + { _nodeAllocClosureInfo = mempty, + _nodeAllocClosureFunSymbol = _identSymbol, _nodeAllocClosureArgs = [] } goConstant :: Core.Constant -> Node goConstant = \case Core.Constant _ (Core.ConstInteger i) -> - Const (ConstInt i) + mkConst (ConstInt i) Core.Constant _ (Core.ConstString s) -> - Const (ConstString s) + mkConst (ConstString s) goApps :: Int -> BinderList MemRef -> Core.Apps -> Node goApps tempSize refs Core.Apps {..} = @@ -91,13 +94,15 @@ genCode infoTable fi = | argsNum > suppliedArgsNum -> AllocClosure $ NodeAllocClosure - { _nodeAllocClosureFunSymbol = _identSymbol, + { _nodeAllocClosureInfo = mempty, + _nodeAllocClosureFunSymbol = _identSymbol, _nodeAllocClosureArgs = suppliedArgs } | argsNum == suppliedArgsNum -> Call $ NodeCall - { _nodeCallType = CallFun _identSymbol, + { _nodeCallInfo = mempty, + _nodeCallType = CallFun _identSymbol, _nodeCallArgs = suppliedArgs } | otherwise -> @@ -108,10 +113,12 @@ genCode infoTable fi = -- with the remaining arguments. CallClosures $ NodeCallClosures - { _nodeCallClosuresFun = + { _nodeCallClosuresInfo = mempty, + _nodeCallClosuresFun = Call $ NodeCall - { _nodeCallType = CallFun _identSymbol, + { _nodeCallInfo = mempty, + _nodeCallType = CallFun _identSymbol, _nodeCallArgs = take argsNum suppliedArgs }, _nodeCallClosuresArgs = nonEmpty' $ drop argsNum suppliedArgs @@ -121,7 +128,8 @@ genCode infoTable fi = Core.FunVar Core.Var {..} -> CallClosures $ NodeCallClosures - { _nodeCallClosuresFun = MemRef $ BL.lookup _varIndex refs, + { _nodeCallClosuresInfo = mempty, + _nodeCallClosuresFun = mkMemRef $ BL.lookup _varIndex refs, _nodeCallClosuresArgs = suppliedArgs' } @@ -131,13 +139,15 @@ genCode infoTable fi = [arg] -> Unop $ NodeUnop - { _nodeUnopOpcode = genUnOp _builtinAppOp, + { _nodeUnopInfo = mempty, + _nodeUnopOpcode = genUnOp _builtinAppOp, _nodeUnopArg = arg } [arg1, arg2] -> Binop $ NodeBinop - { _nodeBinopOpcode = genBinOp _builtinAppOp, + { _nodeBinopInfo = mempty, + _nodeBinopOpcode = genBinOp _builtinAppOp, _nodeBinopArg1 = arg1, _nodeBinopArg2 = arg2 } @@ -149,13 +159,14 @@ genCode infoTable fi = goConstr :: Int -> BinderList MemRef -> Core.Constr -> Node goConstr tempSize refs = \case Core.Constr _ (Core.BuiltinTag Core.TagTrue) _ -> - Const (ConstBool True) + mkConst (ConstBool True) Core.Constr _ (Core.BuiltinTag Core.TagFalse) _ -> - Const (ConstBool False) + mkConst (ConstBool False) Core.Constr {..} -> AllocConstr $ NodeAllocConstr - { _nodeAllocConstrTag = _constrTag, + { _nodeAllocConstrInfo = mempty, + _nodeAllocConstrTag = _constrTag, _nodeAllocConstrArgs = args } where @@ -165,9 +176,10 @@ genCode infoTable fi = goLet tempSize refs (Core.Let {..}) = Save $ NodeSave - { _nodeSaveArg = arg, + { _nodeSaveInfo = mempty, + _nodeSaveArg = arg, _nodeSaveBody = body, - _nodeSaveTempVarInfo = TempVarInfo (Just name) loc + _nodeSaveTempVar = TempVar (Just name) loc } where name = _letItem ^. Core.letItemBinder . Core.binderName @@ -180,7 +192,8 @@ genCode infoTable fi = goCase tempSize refs Core.Case {..} = Case $ NodeCase - { _nodeCaseArg = go tempSize refs _caseValue, + { _nodeCaseInfo = mempty, + _nodeCaseArg = go tempSize refs _caseValue, _nodeCaseInductive = _caseInductive, _nodeCaseBranches = compileCaseBranches _caseBranches, _nodeCaseDefault = fmap compileCaseDefault _caseDefault @@ -201,7 +214,8 @@ genCode infoTable fi = compileCaseBranchNoBinders :: Tag -> Core.Node -> CaseBranch compileCaseBranchNoBinders tag body = CaseBranch - { _caseBranchTag = tag, + { _caseBranchLocation = Nothing, + _caseBranchTag = tag, _caseBranchBody = go tempSize refs body, _caseBranchSave = False } @@ -209,7 +223,8 @@ genCode infoTable fi = compileCaseBranch :: Int -> Tag -> Core.Node -> CaseBranch compileCaseBranch bindersNum tag body = CaseBranch - { _caseBranchTag = tag, + { _caseBranchLocation = Nothing, + _caseBranchTag = tag, _caseBranchBody = go (tempSize + 1) @@ -238,7 +253,8 @@ genCode infoTable fi = goIf tempSize refs Core.If {..} = Branch $ NodeBranch - { _nodeBranchArg = go tempSize refs _ifValue, + { _nodeBranchInfo = mempty, + _nodeBranchArg = go tempSize refs _ifValue, _nodeBranchTrue = go tempSize refs _ifTrue, _nodeBranchFalse = go tempSize refs _ifFalse } diff --git a/src/Juvix/Compiler/Tree/Translation/FromSource.hs b/src/Juvix/Compiler/Tree/Translation/FromSource.hs index 06ba23447d..6e34a72c7f 100644 --- a/src/Juvix/Compiler/Tree/Translation/FromSource.hs +++ b/src/Juvix/Compiler/Tree/Translation/FromSource.hs @@ -24,7 +24,7 @@ parseTreeSig = S.ParserSig { _parserSigBareIdentifier = bareIdentifier, _parserSigParseCode = parseNode, - _parserSigEmptyCode = mkUnop OpFail (Const (ConstString "fail")), + _parserSigEmptyCode = mkUnop OpFail (mkConst (ConstString "fail")), _parserSigEmptyExtra = () } @@ -46,7 +46,7 @@ parseNode :: parseNode = (Binop <$> parseBinop) <|> (Unop <$> parseUnop) - <|> (Const <$> constant) + <|> (Const <$> parseConst) <|> (AllocConstr <$> parseAlloc) <|> (AllocClosure <$> parseCAlloc) <|> (ExtendClosure <$> parseCExtend) @@ -55,7 +55,7 @@ parseNode = <|> (Branch <$> parseBranch) <|> (Case <$> parseCase) <|> (Save <$> parseSave) - <|> (MemRef <$> memRef @Node @()) + <|> (MemRef <$> parseMemRef) parseBinop :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => @@ -78,13 +78,13 @@ parseBinaryOp :: BinaryOpcode -> ParsecS r NodeBinop parseBinaryOp kwd op = do - kw kwd + loc <- onlyInterval (kw kwd) lparen arg1 <- parseNode comma arg2 <- parseNode rparen - return $ NodeBinop op arg1 arg2 + return $ NodeBinop (NodeInfo (Just loc)) op arg1 arg2 parseUnop :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => @@ -102,9 +102,21 @@ parseUnaryOp :: UnaryOpcode -> ParsecS r NodeUnop parseUnaryOp kwd op = do - kw kwd + loc <- onlyInterval (kw kwd) arg <- parens parseNode - return $ NodeUnop op arg + return $ NodeUnop (NodeInfo (Just loc)) op arg + +parseConst :: ParsecS r NodeConstant +parseConst = do + (c, loc) <- interval constant + return $ NodeConstant (NodeInfo (Just loc)) c + +parseMemRef :: + (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => + ParsecS r NodeMemRef +parseMemRef = do + (r, loc) <- interval (memRef @Node @()) + return $ NodeMemRef (NodeInfo (Just loc)) r parseArgs :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => @@ -115,12 +127,13 @@ parseAlloc :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => ParsecS r NodeAllocConstr parseAlloc = do - kw kwAlloc + loc <- onlyInterval (kw kwAlloc) tag <- brackets (constrTag @Node @()) args <- parseArgs return NodeAllocConstr - { _nodeAllocConstrTag = tag, + { _nodeAllocConstrInfo = NodeInfo (Just loc), + _nodeAllocConstrTag = tag, _nodeAllocConstrArgs = args } @@ -128,12 +141,13 @@ parseCAlloc :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => ParsecS r NodeAllocClosure parseCAlloc = do - kw kwCAlloc + loc <- onlyInterval (kw kwCAlloc) sym <- brackets (funSymbol @Node @()) args <- parseArgs return NodeAllocClosure - { _nodeAllocClosureFunSymbol = sym, + { _nodeAllocClosureInfo = NodeInfo (Just loc), + _nodeAllocClosureFunSymbol = sym, _nodeAllocClosureArgs = args } @@ -141,14 +155,15 @@ parseCExtend :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => ParsecS r NodeExtendClosure parseCExtend = do - kw kwCExtend + loc <- onlyInterval (kw kwCExtend) off <- P.getOffset args <- parseArgs case args of arg1 : arg2 : args' -> return NodeExtendClosure - { _nodeExtendClosureFun = arg1, + { _nodeExtendClosureInfo = NodeInfo (Just loc), + _nodeExtendClosureFun = arg1, _nodeExtendClosureArgs = arg2 :| args' } _ -> @@ -159,30 +174,32 @@ parseCall :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => ParsecS r NodeCall parseCall = do - kw kwCall - callDirect <|> callClosure + loc <- onlyInterval (kw kwCall) + callDirect loc <|> callClosure loc where - callDirect :: ParsecS r NodeCall - callDirect = do + callDirect :: Location -> ParsecS r NodeCall + callDirect loc = do lbracket sym <- funSymbol @Node @() rbracket args <- parseArgs return NodeCall - { _nodeCallType = CallFun sym, + { _nodeCallInfo = NodeInfo (Just loc), + _nodeCallType = CallFun sym, _nodeCallArgs = args } - callClosure :: ParsecS r NodeCall - callClosure = do + callClosure :: Location -> ParsecS r NodeCall + callClosure loc = do off <- P.getOffset args <- parseArgs case args of arg : args' -> return NodeCall - { _nodeCallType = CallClosure arg, + { _nodeCallInfo = NodeInfo (Just loc), + _nodeCallType = CallClosure arg, _nodeCallArgs = args' } [] -> @@ -193,7 +210,7 @@ parseCCall :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => ParsecS r NodeCallClosures parseCCall = do - kw kwCCall + loc <- onlyInterval (kw kwCCall) off <- P.getOffset args <- parseArgs case args of @@ -202,7 +219,8 @@ parseCCall = do arg : args' -> return NodeCallClosures - { _nodeCallClosuresFun = arg, + { _nodeCallClosuresInfo = NodeInfo (Just loc), + _nodeCallClosuresFun = arg, _nodeCallClosuresArgs = nonEmpty' args' } [] -> @@ -212,7 +230,7 @@ parseBranch :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => ParsecS r NodeBranch parseBranch = do - kw kwBr + loc <- onlyInterval (kw kwBr) arg <- parens parseNode lbrace br1 <- trueBranch @@ -220,7 +238,8 @@ parseBranch = do rbrace return NodeBranch - { _nodeBranchArg = arg, + { _nodeBranchInfo = NodeInfo (Just loc), + _nodeBranchArg = arg, _nodeBranchTrue = br1, _nodeBranchFalse = br2 } @@ -252,7 +271,7 @@ parseCase :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => ParsecS r NodeCase parseCase = do - kw kwCase + loc <- onlyInterval (kw kwCase) sym <- brackets (indSymbol @Node @()) arg <- parens parseNode lbrace @@ -261,7 +280,8 @@ parseCase = do rbrace return NodeCase - { _nodeCaseInductive = sym, + { _nodeCaseInfo = NodeInfo (Just loc), + _nodeCaseInductive = sym, _nodeCaseArg = arg, _nodeCaseBranches = brs, _nodeCaseDefault = def @@ -272,13 +292,14 @@ caseBranch :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => ParsecS r CaseBranch caseBranch = do - tag <- P.try $ constrTag @Node @() + (tag, loc) <- P.try $ interval (constrTag @Node @()) kw kwColon (bSave, body) <- saveBranch <|> discardBranch optional (kw delimSemicolon) return CaseBranch - { _caseBranchTag = tag, + { _caseBranchLocation = Just loc, + _caseBranchTag = tag, _caseBranchBody = body, _caseBranchSave = bSave } @@ -305,7 +326,7 @@ parseSave :: (Members '[Reader ParserSig, InfoTableBuilder, State LocalParams] r) => ParsecS r NodeSave parseSave = do - kw kwSave + loc' <- onlyInterval (kw kwSave) (mname, loc) <- interval $ optional (brackets identifier) arg <- parens parseNode tmpNum <- lift $ gets (^. localParamsTempIndex) @@ -314,7 +335,8 @@ parseSave = do body <- braces (localS (over localParamsTempIndex (+ 1)) $ localS (over localParamsNameMap updateNames) parseNode) return NodeSave - { _nodeSaveArg = arg, + { _nodeSaveInfo = NodeInfo (Just loc'), + _nodeSaveArg = arg, _nodeSaveBody = body, - _nodeSaveTempVarInfo = TempVarInfo mname (Just loc) + _nodeSaveTempVar = TempVar mname (Just loc) }