packages feed

cimple 0.0.5 → 0.0.6

raw patch · 17 files changed

+989/−1194 lines, 17 filesdep +data-fixdep +recursion-schemesdep +transformers-compatPVP: major bump suggested

API removals or changes: PVP suggests a major version bump

Dependencies added: data-fix, recursion-schemes, transformers-compat

API changes (from Hackage documentation)

- Language.Cimple: Accessor :: lexeme -> [Node attr lexeme] -> Maybe (Node attr lexeme) -> Node attr lexeme
- Language.Cimple: Attr :: attr -> Node attr lexeme -> Node attr lexeme
- Language.Cimple: Class :: Scope -> lexeme -> [Node attr lexeme] -> [Node attr lexeme] -> Node attr lexeme
- Language.Cimple: ClassForward :: lexeme -> [Node attr lexeme] -> Node attr lexeme
- Language.Cimple: CommentWord :: lexeme -> Node attr lexeme
- Language.Cimple: EnumClass :: lexeme -> [Node attr lexeme] -> Node attr lexeme
- Language.Cimple: ErrorDecl :: lexeme -> [Node attr lexeme] -> Node attr lexeme
- Language.Cimple: ErrorFor :: lexeme -> Node attr lexeme
- Language.Cimple: ErrorList :: [Node attr lexeme] -> Node attr lexeme
- Language.Cimple: Event :: lexeme -> Node attr lexeme -> Node attr lexeme
- Language.Cimple: EventParams :: [Node attr lexeme] -> Node attr lexeme
- Language.Cimple: IdTyVar :: LexemeClass
- Language.Cimple: KwBitmask :: LexemeClass
- Language.Cimple: KwClass :: LexemeClass
- Language.Cimple: KwError :: LexemeClass
- Language.Cimple: KwEvent :: LexemeClass
- Language.Cimple: KwNamespace :: LexemeClass
- Language.Cimple: KwThis :: LexemeClass
- Language.Cimple: KwWith :: LexemeClass
- Language.Cimple: Namespace :: Scope -> lexeme -> [Node attr lexeme] -> Node attr lexeme
- Language.Cimple: Property :: Node attr lexeme -> Node attr lexeme -> [Node attr lexeme] -> Node attr lexeme
- Language.Cimple: TyVar :: lexeme -> Node attr lexeme
- Language.Cimple: attrActions :: Applicative f => (iattr -> f oattr) -> AttrActions f iattr oattr text
- Language.Cimple: data Node attr lexeme
- Language.Cimple: doAttr :: AstActions f iattr oattr itext otext -> FilePath -> iattr -> f oattr
- Language.Cimple: mapAst :: (TraverseAst iattr oattr itext otext a b, Applicative f) => AstActions f iattr oattr itext otext -> a -> f b
- Language.Cimple: type AttrActions f iattr oattr text = AstActions f iattr oattr text text
- Language.Cimple.Diagnostics: at :: Node a (Lexeme Text) -> Lexeme Text
+ Language.Cimple: data NodeF lexeme a
+ Language.Cimple: type Node lexeme = Fix (NodeF lexeme)
+ Language.Cimple.Diagnostics: instance Language.Cimple.Diagnostics.HasLocation (Language.Cimple.Lexer.Lexeme text)
+ Language.Cimple.Diagnostics: instance Language.Cimple.Diagnostics.HasLocation lexeme => Language.Cimple.Diagnostics.HasLocation (Language.Cimple.AST.Node lexeme)
- Language.Cimple: ArrayAccess :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: ArrayAccess :: a -> a -> NodeF lexeme a
- Language.Cimple: AssignExpr :: Node attr lexeme -> AssignOp -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: AssignExpr :: a -> AssignOp -> a -> NodeF lexeme a
- Language.Cimple: BinaryExpr :: Node attr lexeme -> BinaryOp -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: BinaryExpr :: a -> BinaryOp -> a -> NodeF lexeme a
- Language.Cimple: Break :: Node attr lexeme
+ Language.Cimple: Break :: NodeF lexeme a
- Language.Cimple: Case :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: Case :: a -> a -> NodeF lexeme a
- Language.Cimple: CastExpr :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: CastExpr :: a -> a -> NodeF lexeme a
- Language.Cimple: Comment :: CommentStyle -> lexeme -> [Node attr lexeme] -> lexeme -> Node attr lexeme
+ Language.Cimple: Comment :: CommentStyle -> lexeme -> [lexeme] -> lexeme -> NodeF lexeme a
- Language.Cimple: CommentBlock :: lexeme -> Node attr lexeme
+ Language.Cimple: CommentBlock :: lexeme -> NodeF lexeme a
- Language.Cimple: CommentExpr :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: CommentExpr :: a -> a -> NodeF lexeme a
- Language.Cimple: Commented :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: Commented :: a -> a -> NodeF lexeme a
- Language.Cimple: CompoundExpr :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: CompoundExpr :: a -> a -> NodeF lexeme a
- Language.Cimple: CompoundStmt :: [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: CompoundStmt :: [a] -> NodeF lexeme a
- Language.Cimple: ConstDecl :: Node attr lexeme -> lexeme -> Node attr lexeme
+ Language.Cimple: ConstDecl :: a -> lexeme -> NodeF lexeme a
- Language.Cimple: ConstDefn :: Scope -> Node attr lexeme -> lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: ConstDefn :: Scope -> a -> lexeme -> a -> NodeF lexeme a
- Language.Cimple: Continue :: Node attr lexeme
+ Language.Cimple: Continue :: NodeF lexeme a
- Language.Cimple: CopyrightDecl :: lexeme -> Maybe lexeme -> [lexeme] -> Node attr lexeme
+ Language.Cimple: CopyrightDecl :: lexeme -> Maybe lexeme -> [lexeme] -> NodeF lexeme a
- Language.Cimple: DeclSpecArray :: Node attr lexeme -> Maybe (Node attr lexeme) -> Node attr lexeme
+ Language.Cimple: DeclSpecArray :: a -> Maybe a -> NodeF lexeme a
- Language.Cimple: DeclSpecVar :: lexeme -> Node attr lexeme
+ Language.Cimple: DeclSpecVar :: lexeme -> NodeF lexeme a
- Language.Cimple: Declarator :: Node attr lexeme -> Maybe (Node attr lexeme) -> Node attr lexeme
+ Language.Cimple: Declarator :: a -> Maybe a -> NodeF lexeme a
- Language.Cimple: Default :: Node attr lexeme -> Node attr lexeme
+ Language.Cimple: Default :: a -> NodeF lexeme a
- Language.Cimple: DoWhileStmt :: [Node attr lexeme] -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: DoWhileStmt :: a -> a -> NodeF lexeme a
- Language.Cimple: Ellipsis :: Node attr lexeme
+ Language.Cimple: Ellipsis :: NodeF lexeme a
- Language.Cimple: EnumConsts :: Maybe lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: EnumConsts :: Maybe lexeme -> [a] -> NodeF lexeme a
- Language.Cimple: EnumDecl :: lexeme -> [Node attr lexeme] -> lexeme -> Node attr lexeme
+ Language.Cimple: EnumDecl :: lexeme -> [a] -> lexeme -> NodeF lexeme a
- Language.Cimple: Enumerator :: lexeme -> Maybe (Node attr lexeme) -> Node attr lexeme
+ Language.Cimple: Enumerator :: lexeme -> Maybe a -> NodeF lexeme a
- Language.Cimple: ExternC :: [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: ExternC :: [a] -> NodeF lexeme a
- Language.Cimple: ForStmt :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: ForStmt :: a -> a -> a -> a -> NodeF lexeme a
- Language.Cimple: FunctionCall :: Node attr lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: FunctionCall :: a -> [a] -> NodeF lexeme a
- Language.Cimple: FunctionDecl :: Scope -> Node attr lexeme -> Maybe (Node attr lexeme) -> Node attr lexeme
+ Language.Cimple: FunctionDecl :: Scope -> a -> NodeF lexeme a
- Language.Cimple: FunctionDefn :: Scope -> Node attr lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: FunctionDefn :: Scope -> a -> a -> NodeF lexeme a
- Language.Cimple: FunctionParam :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: FunctionParam :: a -> a -> NodeF lexeme a
- Language.Cimple: FunctionPrototype :: Node attr lexeme -> lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: FunctionPrototype :: a -> lexeme -> [a] -> NodeF lexeme a
- Language.Cimple: Goto :: lexeme -> Node attr lexeme
+ Language.Cimple: Goto :: lexeme -> NodeF lexeme a
- Language.Cimple: IfStmt :: Node attr lexeme -> [Node attr lexeme] -> Maybe (Node attr lexeme) -> Node attr lexeme
+ Language.Cimple: IfStmt :: a -> a -> Maybe a -> NodeF lexeme a
- Language.Cimple: InitialiserList :: [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: InitialiserList :: [a] -> NodeF lexeme a
- Language.Cimple: Label :: lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: Label :: lexeme -> a -> NodeF lexeme a
- Language.Cimple: LicenseDecl :: lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: LicenseDecl :: lexeme -> [a] -> NodeF lexeme a
- Language.Cimple: LiteralExpr :: LiteralType -> lexeme -> Node attr lexeme
+ Language.Cimple: LiteralExpr :: LiteralType -> lexeme -> NodeF lexeme a
- Language.Cimple: MacroBodyFunCall :: Node attr lexeme -> Node attr lexeme
+ Language.Cimple: MacroBodyFunCall :: a -> NodeF lexeme a
- Language.Cimple: MacroBodyStmt :: [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: MacroBodyStmt :: a -> NodeF lexeme a
- Language.Cimple: MacroParam :: lexeme -> Node attr lexeme
+ Language.Cimple: MacroParam :: lexeme -> NodeF lexeme a
- Language.Cimple: MemberAccess :: Node attr lexeme -> lexeme -> Node attr lexeme
+ Language.Cimple: MemberAccess :: a -> lexeme -> NodeF lexeme a
- Language.Cimple: MemberDecl :: Node attr lexeme -> Node attr lexeme -> Maybe lexeme -> Node attr lexeme
+ Language.Cimple: MemberDecl :: a -> a -> Maybe lexeme -> NodeF lexeme a
- Language.Cimple: ParenExpr :: Node attr lexeme -> Node attr lexeme
+ Language.Cimple: ParenExpr :: a -> NodeF lexeme a
- Language.Cimple: PointerAccess :: Node attr lexeme -> lexeme -> Node attr lexeme
+ Language.Cimple: PointerAccess :: a -> lexeme -> NodeF lexeme a
- Language.Cimple: PreprocDefine :: lexeme -> Node attr lexeme
+ Language.Cimple: PreprocDefine :: lexeme -> NodeF lexeme a
- Language.Cimple: PreprocDefineConst :: lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: PreprocDefineConst :: lexeme -> a -> NodeF lexeme a
- Language.Cimple: PreprocDefineMacro :: lexeme -> [Node attr lexeme] -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: PreprocDefineMacro :: lexeme -> [a] -> a -> NodeF lexeme a
- Language.Cimple: PreprocDefined :: lexeme -> Node attr lexeme
+ Language.Cimple: PreprocDefined :: lexeme -> NodeF lexeme a
- Language.Cimple: PreprocElif :: Node attr lexeme -> [Node attr lexeme] -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: PreprocElif :: a -> [a] -> a -> NodeF lexeme a
- Language.Cimple: PreprocElse :: [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: PreprocElse :: [a] -> NodeF lexeme a
- Language.Cimple: PreprocIf :: Node attr lexeme -> [Node attr lexeme] -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: PreprocIf :: a -> [a] -> a -> NodeF lexeme a
- Language.Cimple: PreprocIfdef :: lexeme -> [Node attr lexeme] -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: PreprocIfdef :: lexeme -> [a] -> a -> NodeF lexeme a
- Language.Cimple: PreprocIfndef :: lexeme -> [Node attr lexeme] -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: PreprocIfndef :: lexeme -> [a] -> a -> NodeF lexeme a
- Language.Cimple: PreprocInclude :: lexeme -> Node attr lexeme
+ Language.Cimple: PreprocInclude :: lexeme -> NodeF lexeme a
- Language.Cimple: PreprocScopedDefine :: Node attr lexeme -> [Node attr lexeme] -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: PreprocScopedDefine :: a -> [a] -> a -> NodeF lexeme a
- Language.Cimple: PreprocUndef :: lexeme -> Node attr lexeme
+ Language.Cimple: PreprocUndef :: lexeme -> NodeF lexeme a
- Language.Cimple: Return :: Maybe (Node attr lexeme) -> Node attr lexeme
+ Language.Cimple: Return :: Maybe a -> NodeF lexeme a
- Language.Cimple: SizeofExpr :: Node attr lexeme -> Node attr lexeme
+ Language.Cimple: SizeofExpr :: a -> NodeF lexeme a
- Language.Cimple: SizeofType :: Node attr lexeme -> Node attr lexeme
+ Language.Cimple: SizeofType :: a -> NodeF lexeme a
- Language.Cimple: StaticAssert :: Node attr lexeme -> lexeme -> Node attr lexeme
+ Language.Cimple: StaticAssert :: a -> lexeme -> NodeF lexeme a
- Language.Cimple: Struct :: lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: Struct :: lexeme -> [a] -> NodeF lexeme a
- Language.Cimple: SwitchStmt :: Node attr lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: SwitchStmt :: a -> [a] -> NodeF lexeme a
- Language.Cimple: TernaryExpr :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: TernaryExpr :: a -> a -> a -> NodeF lexeme a
- Language.Cimple: TyConst :: Node attr lexeme -> Node attr lexeme
+ Language.Cimple: TyConst :: a -> NodeF lexeme a
- Language.Cimple: TyFunc :: lexeme -> Node attr lexeme
+ Language.Cimple: TyFunc :: lexeme -> NodeF lexeme a
- Language.Cimple: TyPointer :: Node attr lexeme -> Node attr lexeme
+ Language.Cimple: TyPointer :: a -> NodeF lexeme a
- Language.Cimple: TyStd :: lexeme -> Node attr lexeme
+ Language.Cimple: TyStd :: lexeme -> NodeF lexeme a
- Language.Cimple: TyStruct :: lexeme -> Node attr lexeme
+ Language.Cimple: TyStruct :: lexeme -> NodeF lexeme a
- Language.Cimple: TyUserDefined :: lexeme -> Node attr lexeme
+ Language.Cimple: TyUserDefined :: lexeme -> NodeF lexeme a
- Language.Cimple: Typedef :: Node attr lexeme -> lexeme -> Node attr lexeme
+ Language.Cimple: Typedef :: a -> lexeme -> NodeF lexeme a
- Language.Cimple: TypedefFunction :: Node attr lexeme -> Node attr lexeme
+ Language.Cimple: TypedefFunction :: a -> NodeF lexeme a
- Language.Cimple: UnaryExpr :: UnaryOp -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: UnaryExpr :: UnaryOp -> a -> NodeF lexeme a
- Language.Cimple: Union :: lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: Union :: lexeme -> [a] -> NodeF lexeme a
- Language.Cimple: VLA :: Node attr lexeme -> lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: VLA :: a -> lexeme -> a -> NodeF lexeme a
- Language.Cimple: VarDecl :: Node attr lexeme -> Node attr lexeme -> Node attr lexeme
+ Language.Cimple: VarDecl :: a -> a -> NodeF lexeme a
- Language.Cimple: VarExpr :: lexeme -> Node attr lexeme
+ Language.Cimple: VarExpr :: lexeme -> NodeF lexeme a
- Language.Cimple: WhileStmt :: Node attr lexeme -> [Node attr lexeme] -> Node attr lexeme
+ Language.Cimple: WhileStmt :: a -> a -> NodeF lexeme a
- Language.Cimple: astActions :: Applicative f => (iattr -> f oattr) -> (itext -> f otext) -> AstActions f iattr oattr itext otext
+ Language.Cimple: astActions :: Applicative f => (itext -> f otext) -> AstActions f itext otext
- Language.Cimple: defaultActions :: IdentityActions (State a) () Text
+ Language.Cimple: defaultActions :: AstActions state
- Language.Cimple: doFile :: AstActions f iattr oattr itext otext -> (FilePath, [Node iattr (Lexeme itext)]) -> f (FilePath, [Node oattr (Lexeme otext)]) -> f (FilePath, [Node oattr (Lexeme otext)])
+ Language.Cimple: doFile :: AstActions f itext otext -> (FilePath, [Node (Lexeme itext)]) -> f (FilePath, [Node (Lexeme otext)]) -> f (FilePath, [Node (Lexeme otext)])
- Language.Cimple: doFiles :: AstActions f iattr oattr itext otext -> [(FilePath, [Node iattr (Lexeme itext)])] -> f [(FilePath, [Node oattr (Lexeme otext)])] -> f [(FilePath, [Node oattr (Lexeme otext)])]
+ Language.Cimple: doFiles :: AstActions f itext otext -> [(FilePath, [Node (Lexeme itext)])] -> f [(FilePath, [Node (Lexeme otext)])] -> f [(FilePath, [Node (Lexeme otext)])]
- Language.Cimple: doLexeme :: AstActions f iattr oattr itext otext -> FilePath -> Lexeme itext -> f (Lexeme otext) -> f (Lexeme otext)
+ Language.Cimple: doLexeme :: AstActions f itext otext -> FilePath -> Lexeme itext -> f (Lexeme otext) -> f (Lexeme otext)
- Language.Cimple: doLexemes :: AstActions f iattr oattr itext otext -> FilePath -> [Lexeme itext] -> f [Lexeme otext] -> f [Lexeme otext]
+ Language.Cimple: doLexemes :: AstActions f itext otext -> FilePath -> [Lexeme itext] -> f [Lexeme otext] -> f [Lexeme otext]
- Language.Cimple: doNode :: AstActions f iattr oattr itext otext -> FilePath -> Node iattr (Lexeme itext) -> f (Node oattr (Lexeme otext)) -> f (Node oattr (Lexeme otext))
+ Language.Cimple: doNode :: AstActions f itext otext -> FilePath -> Node (Lexeme itext) -> f (Node (Lexeme otext)) -> f (Node (Lexeme otext))
- Language.Cimple: doNodes :: AstActions f iattr oattr itext otext -> FilePath -> [Node iattr (Lexeme itext)] -> f [Node oattr (Lexeme otext)] -> f [Node oattr (Lexeme otext)]
+ Language.Cimple: doNodes :: AstActions f itext otext -> FilePath -> [Node (Lexeme itext)] -> f [Node (Lexeme otext)] -> f [Node (Lexeme otext)]
- Language.Cimple: doText :: AstActions f iattr oattr itext otext -> FilePath -> itext -> f otext
+ Language.Cimple: doText :: AstActions f itext otext -> FilePath -> itext -> f otext
- Language.Cimple: identityActions :: Applicative f => AstActions f attr attr text text
+ Language.Cimple: identityActions :: Applicative f => AstActions f text text
- Language.Cimple: textActions :: Applicative f => (itext -> f otext) -> TextActions f attr itext otext
+ Language.Cimple: textActions :: Applicative f => (itext -> f otext) -> TextActions f itext otext
- Language.Cimple: traverseAst :: (TraverseAst iattr oattr itext otext a a, Applicative f) => AstActions f iattr oattr itext otext -> a -> f a
+ Language.Cimple: traverseAst :: (TraverseAst itext otext a, Applicative f) => AstActions f itext otext -> a -> f (Mapped itext otext a)
- Language.Cimple: type AstActions a = IdentityActions (State a) () Text
+ Language.Cimple: type AstActions a = IdentityActions (State a) Text
- Language.Cimple: type IdentityActions f attr text = AstActions f attr attr text text
+ Language.Cimple: type IdentityActions f text = AstActions f text text
- Language.Cimple: type TextActions f attr itext otext = AstActions f attr attr itext otext
+ Language.Cimple: type TextActions f itext otext = AstActions f itext otext
- Language.Cimple.Diagnostics: sloc :: FilePath -> Lexeme text -> Text
+ Language.Cimple.Diagnostics: sloc :: HasLocation a => FilePath -> a -> Text
- Language.Cimple.Diagnostics: warn :: HasDiagnostics diags => FilePath -> Lexeme Text -> Text -> DiagnosticsT diags ()
+ Language.Cimple.Diagnostics: warn :: (HasLocation at, HasDiagnostics diags) => FilePath -> at -> Text -> DiagnosticsT diags ()
- Language.Cimple.Pretty: ppTranslationUnit :: Show a => [Node a (Lexeme Text)] -> Doc
+ Language.Cimple.Pretty: ppTranslationUnit :: [Node (Lexeme Text)] -> Doc

Files

cimple.cabal view
@@ -1,12 +1,12 @@ name:                 cimple-version:              0.0.5+version:              0.0.6 synopsis:             Simple C-like programming language homepage:             https://toktok.github.io/ license:              GPL-3 license-file:         LICENSE author:               Iphigenia Df <iphydf@gmail.com> maintainer:           Iphigenia Df <iphydf@gmail.com>-copyright:            Copyright (c) 2016-2020, Iphigenia Df+copyright:            Copyright (c) 2016-2022, Iphigenia Df category:             Data stability:            Experimental cabal-version:        >= 1.10@@ -33,6 +33,7 @@     , Language.Cimple.Program   other-modules:       Language.Cimple.AST+    , Language.Cimple.Flatten     , Language.Cimple.Graph     , Language.Cimple.Lexer     , Language.Cimple.Parser@@ -48,10 +49,13 @@     , array     , bytestring     , containers+    , data-fix     , filepath     , groom     , mtl+    , recursion-schemes     , text+    , transformers-compat  executable cimplefmt   default-language: Haskell2010@@ -121,5 +125,7 @@       base < 5     , ansi-wl-pprint     , cimple+    , data-fix     , hspec     , text+    , transformers-compat
src/Language/Cimple.hs view
@@ -13,7 +13,7 @@ import           Language.Cimple.Tokens      as X import           Language.Cimple.TraverseAst as X -type AstActions a = X.IdentityActions (State a) () Text+type AstActions a = X.IdentityActions (State a) Text -defaultActions :: X.IdentityActions (State a) () Text+defaultActions :: AstActions state defaultActions = X.identityActions
src/Language/Cimple/AST.hs view
@@ -1,127 +1,122 @@-{-# LANGUAGE DeriveFunctor     #-}-{-# LANGUAGE DeriveGeneric     #-}-{-# LANGUAGE DeriveTraversable #-}-{-# LANGUAGE StrictData        #-}+{-# LANGUAGE DeriveFunctor      #-}+{-# LANGUAGE DeriveGeneric      #-}+{-# LANGUAGE DeriveTraversable  #-}+{-# LANGUAGE DerivingVia        #-}+{-# LANGUAGE FlexibleInstances  #-}+{-# LANGUAGE StandaloneDeriving #-}+{-# LANGUAGE StrictData         #-} module Language.Cimple.AST     ( AssignOp (..)     , BinaryOp (..)     , UnaryOp (..)     , LiteralType (..)-    , Node (..)+    , Node, NodeF (..)     , Scope (..)     , CommentStyle (..)     ) where -import           Data.Aeson   (FromJSON, ToJSON)-import           GHC.Generics (Generic)+import           Data.Aeson                   (FromJSON, ToJSON)+import           Data.Fix                     (Fix)+import           Data.Functor.Classes         (Eq1, Read1, Show1)+import           Data.Functor.Classes.Generic (FunctorClassesDefault (..))+import           GHC.Generics                 (Generic, Generic1) -data Node attr lexeme-    = Attr attr (Node attr lexeme)+data NodeF lexeme a     -- Preprocessor-    | PreprocInclude lexeme+    = PreprocInclude lexeme     | PreprocDefine lexeme-    | PreprocDefineConst lexeme (Node attr lexeme)-    | PreprocDefineMacro lexeme [Node attr lexeme] (Node attr lexeme)-    | PreprocIf (Node attr lexeme) [Node attr lexeme] (Node attr lexeme)-    | PreprocIfdef lexeme [Node attr lexeme] (Node attr lexeme)-    | PreprocIfndef lexeme [Node attr lexeme] (Node attr lexeme)-    | PreprocElse [Node attr lexeme]-    | PreprocElif (Node attr lexeme) [Node attr lexeme] (Node attr lexeme)+    | PreprocDefineConst lexeme a+    | PreprocDefineMacro lexeme [a] a+    | PreprocIf a [a] a+    | PreprocIfdef lexeme [a] a+    | PreprocIfndef lexeme [a] a+    | PreprocElse [a]+    | PreprocElif a [a] a     | PreprocUndef lexeme     | PreprocDefined lexeme-    | PreprocScopedDefine (Node attr lexeme) [Node attr lexeme] (Node attr lexeme)-    | MacroBodyStmt [Node attr lexeme]-    | MacroBodyFunCall (Node attr lexeme)+    | PreprocScopedDefine a [a] a+    | MacroBodyStmt a+    | MacroBodyFunCall a     | MacroParam lexeme-    | StaticAssert (Node attr lexeme) lexeme+    | StaticAssert a lexeme     -- Comments-    | LicenseDecl lexeme [Node attr lexeme]+    | LicenseDecl lexeme [a]     | CopyrightDecl lexeme (Maybe lexeme) [lexeme]-    | Comment CommentStyle lexeme [Node attr lexeme] lexeme+    | Comment CommentStyle lexeme [lexeme] lexeme     | CommentBlock lexeme-    | CommentWord lexeme-    | Commented (Node attr lexeme) (Node attr lexeme)+    | Commented a a     -- Namespace-like blocks-    | ExternC [Node attr lexeme]-    | Class Scope lexeme [Node attr lexeme] [Node attr lexeme]-    | Namespace Scope lexeme [Node attr lexeme]+    | ExternC [a]     -- Statements-    | CompoundStmt [Node attr lexeme]+    | CompoundStmt [a]     | Break     | Goto lexeme     | Continue-    | Return (Maybe (Node attr lexeme))-    | SwitchStmt (Node attr lexeme) [Node attr lexeme]-    | IfStmt (Node attr lexeme) [Node attr lexeme] (Maybe (Node attr lexeme))-    | ForStmt (Node attr lexeme) (Node attr lexeme) (Node attr lexeme) [Node attr lexeme]-    | WhileStmt (Node attr lexeme) [Node attr lexeme]-    | DoWhileStmt [Node attr lexeme] (Node attr lexeme)-    | Case (Node attr lexeme) (Node attr lexeme)-    | Default (Node attr lexeme)-    | Label lexeme (Node attr lexeme)+    | Return (Maybe a)+    | SwitchStmt a [a]+    | IfStmt a a (Maybe a)+    | ForStmt a a a a+    | WhileStmt a a+    | DoWhileStmt a a+    | Case a a+    | Default a+    | Label lexeme a     -- Variable declarations-    | VLA (Node attr lexeme) lexeme (Node attr lexeme)-    | VarDecl (Node attr lexeme) (Node attr lexeme)-    | Declarator (Node attr lexeme) (Maybe (Node attr lexeme))+    | VLA a lexeme a+    | VarDecl a a+    | Declarator a (Maybe a)     | DeclSpecVar lexeme-    | DeclSpecArray (Node attr lexeme) (Maybe (Node attr lexeme))+    | DeclSpecArray a (Maybe a)     -- Expressions-    | InitialiserList [Node attr lexeme]-    | UnaryExpr UnaryOp (Node attr lexeme)-    | BinaryExpr (Node attr lexeme) BinaryOp (Node attr lexeme)-    | TernaryExpr (Node attr lexeme) (Node attr lexeme) (Node attr lexeme)-    | AssignExpr (Node attr lexeme) AssignOp (Node attr lexeme)-    | ParenExpr (Node attr lexeme)-    | CastExpr (Node attr lexeme) (Node attr lexeme)-    | CompoundExpr (Node attr lexeme) (Node attr lexeme)-    | SizeofExpr (Node attr lexeme)-    | SizeofType (Node attr lexeme)+    | InitialiserList [a]+    | UnaryExpr UnaryOp a+    | BinaryExpr a BinaryOp a+    | TernaryExpr a a a+    | AssignExpr a AssignOp a+    | ParenExpr a+    | CastExpr a a+    | CompoundExpr a a+    | SizeofExpr a+    | SizeofType a     | LiteralExpr LiteralType lexeme     | VarExpr lexeme-    | MemberAccess (Node attr lexeme) lexeme-    | PointerAccess (Node attr lexeme) lexeme-    | ArrayAccess (Node attr lexeme) (Node attr lexeme)-    | FunctionCall (Node attr lexeme) [Node attr lexeme]-    | CommentExpr (Node attr lexeme) (Node attr lexeme)+    | MemberAccess a lexeme+    | PointerAccess a lexeme+    | ArrayAccess a a+    | FunctionCall a [a]+    | CommentExpr a a     -- Type definitions-    | EnumClass lexeme [Node attr lexeme]-    | EnumConsts (Maybe lexeme) [Node attr lexeme]-    | EnumDecl lexeme [Node attr lexeme] lexeme-    | Enumerator lexeme (Maybe (Node attr lexeme))-    | ClassForward lexeme [Node attr lexeme]-    | Typedef (Node attr lexeme) lexeme-    | TypedefFunction (Node attr lexeme)-    | Struct lexeme [Node attr lexeme]-    | Union lexeme [Node attr lexeme]-    | MemberDecl (Node attr lexeme) (Node attr lexeme) (Maybe lexeme)-    | TyConst (Node attr lexeme)-    | TyPointer (Node attr lexeme)+    | EnumConsts (Maybe lexeme) [a]+    | EnumDecl lexeme [a] lexeme+    | Enumerator lexeme (Maybe a)+    | Typedef a lexeme+    | TypedefFunction a+    | Struct lexeme [a]+    | Union lexeme [a]+    | MemberDecl a a (Maybe lexeme)+    | TyConst a+    | TyPointer a     | TyStruct lexeme     | TyFunc lexeme     | TyStd lexeme-    | TyVar lexeme     | TyUserDefined lexeme     -- Functions-    | FunctionDecl Scope (Node attr lexeme) (Maybe (Node attr lexeme))-    | FunctionDefn Scope (Node attr lexeme) [Node attr lexeme]-    | FunctionPrototype (Node attr lexeme) lexeme [Node attr lexeme]-    | FunctionParam (Node attr lexeme) (Node attr lexeme)-    | Event lexeme (Node attr lexeme)-    | EventParams [Node attr lexeme]-    | Property (Node attr lexeme) (Node attr lexeme) [Node attr lexeme]-    | Accessor lexeme [Node attr lexeme] (Maybe (Node attr lexeme))-    | ErrorDecl lexeme [Node attr lexeme]-    | ErrorList [Node attr lexeme]-    | ErrorFor lexeme+    | FunctionDecl Scope a+    | FunctionDefn Scope a a+    | FunctionPrototype a lexeme [a]+    | FunctionParam a a     | Ellipsis     -- Constants-    | ConstDecl (Node attr lexeme) lexeme-    | ConstDefn Scope (Node attr lexeme) lexeme (Node attr lexeme)-    deriving (Show, Eq, Generic, Functor, Foldable, Traversable)+    | ConstDecl a lexeme+    | ConstDefn Scope a lexeme a+    deriving (Show, Read, Eq, Generic, Generic1, Functor, Foldable, Traversable)+    deriving (Show1, Read1, Eq1) via FunctorClassesDefault (NodeF lexeme) -instance (FromJSON attr, FromJSON lexeme) => FromJSON (Node attr lexeme)-instance (ToJSON attr, ToJSON lexeme) => ToJSON (Node attr lexeme)+type Node lexeme = Fix (NodeF lexeme) +instance (FromJSON lexeme, FromJSON a) => FromJSON (NodeF lexeme a)+instance (ToJSON lexeme, ToJSON a) => ToJSON (NodeF lexeme a)+ data AssignOp     = AopEq     | AopMul@@ -134,7 +129,7 @@     | AopMod     | AopLsh     | AopRsh-    deriving (Show, Eq, Generic)+    deriving (Show, Read, Eq, Generic)  instance FromJSON AssignOp instance ToJSON AssignOp@@ -158,7 +153,7 @@     | BopGt     | BopGe     | BopRsh-    deriving (Show, Eq, Generic)+    deriving (Show, Read, Eq, Generic)  instance FromJSON BinaryOp instance ToJSON BinaryOp@@ -171,7 +166,7 @@     | UopDeref     | UopIncr     | UopDecr-    deriving (Show, Eq, Generic)+    deriving (Show, Read, Eq, Generic)  instance FromJSON UnaryOp instance ToJSON UnaryOp@@ -182,7 +177,7 @@     | Bool     | String     | ConstId-    deriving (Show, Eq, Generic)+    deriving (Show, Read, Eq, Generic)  instance FromJSON LiteralType instance ToJSON LiteralType@@ -190,7 +185,7 @@ data Scope     = Global     | Static-    deriving (Show, Eq, Generic)+    deriving (Show, Read, Eq, Generic)  instance FromJSON Scope instance ToJSON Scope@@ -199,7 +194,7 @@     = Regular     | Doxygen     | Block-    deriving (Show, Eq, Generic)+    deriving (Show, Read, Eq, Generic)  instance FromJSON CommentStyle instance ToJSON CommentStyle
src/Language/Cimple/Diagnostics.hs view
@@ -6,22 +6,26 @@   , HasDiagnostics (..)   , warn   , sloc-  , at   ) where  import           Control.Monad.State.Lazy (State) import qualified Control.Monad.State.Lazy as State+import           Data.Fix                 (foldFix) import           Data.Text                (Text) import qualified Data.Text                as Text import           Language.Cimple.AST      (Node)-import           Language.Cimple.Lexer    (AlexPosn (..), Lexeme (..),-                                           lexemeLine)-import           Language.Cimple.Tokens   (LexemeClass (..))+import qualified Language.Cimple.Flatten  as Flatten+import           Language.Cimple.Lexer    (Lexeme (..), lexemeLine)  type DiagnosticsT diags a = State diags a type Diagnostics a = DiagnosticsT [Text] a +warn+    :: (HasLocation at, HasDiagnostics diags)+    => FilePath -> at -> Text -> DiagnosticsT diags ()+warn file l w = State.modify (addDiagnostic $ sloc file l <> ": " <> w) + class HasDiagnostics a where     addDiagnostic :: Text -> a -> a @@ -29,16 +33,14 @@     addDiagnostic = (:)  -warn :: HasDiagnostics diags => FilePath -> Lexeme Text -> Text -> DiagnosticsT diags ()-warn file l w = State.modify (addDiagnostic $ sloc file l <> ": " <> w)---sloc :: FilePath -> Lexeme text -> Text-sloc file l = Text.pack file <> ":" <> Text.pack (show (lexemeLine l))+class HasLocation a where+    sloc :: FilePath -> a -> Text +instance HasLocation (Lexeme text) where+    sloc file l = Text.pack file <> ":" <> Text.pack (show (lexemeLine l)) -at :: Node a (Lexeme Text) -> Lexeme Text-at n =-    case foldMap (:[]) n of-        []  -> L (AlexPn 0 0 0) Error "unknown source location"-        l:_ -> l+instance HasLocation lexeme => HasLocation (Node lexeme) where+    sloc file n =+        case foldFix Flatten.lexemes n of+            []  -> Text.pack file <> ":0:0"+            l:_ -> sloc file l
+ src/Language/Cimple/Flatten.hs view
@@ -0,0 +1,62 @@+{-# LANGUAGE DefaultSignatures     #-}+{-# LANGUAGE FlexibleContexts      #-}+{-# LANGUAGE FlexibleInstances     #-}+{-# LANGUAGE MultiParamTypeClasses #-}+{-# LANGUAGE StrictData            #-}+{-# LANGUAGE TypeOperators         #-}+module Language.Cimple.Flatten (lexemes) where++import           Data.Maybe          (maybeToList)+import           GHC.Generics+import           Language.Cimple.AST (AssignOp, BinaryOp, CommentStyle,+                                      LiteralType, NodeF (..), Scope, UnaryOp)++class Concats t a where+    concats :: t -> [a]++    default concats :: (Generic t, GenConcats (Rep t) a) => t -> [a]+    concats = gconcats . from++class GenConcats f a where+    gconcats :: f p -> [a]++instance GenConcats U1 a where+    gconcats U1 = []++instance (GenConcats f a, GenConcats g a) => GenConcats (f :+: g) a where+    gconcats (L1 x) = gconcats x+    gconcats (R1 x) = gconcats x++instance (GenConcats f a, GenConcats g a) => GenConcats (f :*: g) a where+    gconcats (x :*: y) = gconcats x ++ gconcats y++instance GenConcats f a => GenConcats (M1 i t f) a where+    gconcats (M1 x) = gconcats x++class GenConcatsFlatten t a where+    gconcatsFlatten :: t -> [a]++instance GenConcatsFlatten UnaryOp      a where gconcatsFlatten = const []+instance GenConcatsFlatten BinaryOp     a where gconcatsFlatten = const []+instance GenConcatsFlatten AssignOp     a where gconcatsFlatten = const []+instance GenConcatsFlatten Scope        a where gconcatsFlatten = const []+instance GenConcatsFlatten CommentStyle a where gconcatsFlatten = const []+instance GenConcatsFlatten LiteralType  a where gconcatsFlatten = const []++instance GenConcatsFlatten b a => GenConcatsFlatten (Maybe b) a where+    gconcatsFlatten = gconcatsFlatten . maybeToList++instance {-# OVERLAPPING #-} GenConcatsFlatten a a where+    gconcatsFlatten = pure++instance {-# OVERLAPPABLE #-} GenConcatsFlatten b a => GenConcatsFlatten [b] a where+    gconcatsFlatten = concatMap gconcatsFlatten++instance GenConcatsFlatten t a => GenConcats (Rec0 t) a where+    gconcats (K1 x) = gconcatsFlatten x++-- Uses the default signature, which delegates to the generic stuff+instance Concats (NodeF a [a]) a++lexemes :: NodeF lexeme [lexeme] -> [lexeme]+lexemes = concats
src/Language/Cimple/IO.hs view
@@ -14,24 +14,24 @@ import           Data.Text                       (Text) import qualified Data.Text                       as Text import qualified Data.Text.Encoding              as Text-import           Language.Cimple.AST             (Node (..))+import           Language.Cimple.AST             (Node) import           Language.Cimple.Lexer           (Lexeme, runAlex) import qualified Language.Cimple.Parser          as Parser import           Language.Cimple.Program         (Program) import qualified Language.Cimple.Program         as Program import           Language.Cimple.TranslationUnit (TranslationUnit)-import           Language.Cimple.TraverseAst     (TextActions, mapAst,-                                                  textActions)+import           Language.Cimple.TraverseAst     (TextActions, textActions,+                                                  traverseAst) import qualified Language.Cimple.TreeParser      as TreeParser -type StringNode = Node () (Lexeme String)-type TextNode = Node () (Lexeme Text)+type StringNode = Node (Lexeme String)+type TextNode = Node (Lexeme Text)  toTextAst :: [StringNode] -> [TextNode] toTextAst stringAst =-    evalState (mapAst cacheActions stringAst) Map.empty+    evalState (traverseAst cacheActions stringAst) Map.empty   where-    cacheActions :: TextActions (State (Map String Text)) () String Text+    cacheActions :: TextActions (State (Map String Text)) String Text     cacheActions = textActions $ \s -> do         m <- get         case Map.lookup s m of
src/Language/Cimple/Lexer.x view
@@ -114,35 +114,28 @@ <0>		"#define"				{ mkL PpDefine `andBegin` ppSC } <0>		"#undef"				{ mkL PpUndef } <0>		"#include"				{ mkL PpInclude }-<0,ppSC>	"bitmask"				{ mkL KwBitmask } <0,ppSC>	"break"					{ mkL KwBreak } <0,ppSC>	"case"					{ mkL KwCase }-<0,ppSC>	"class"					{ mkL KwClass } <0,ppSC>	"const"					{ mkL KwConst } <0,ppSC>	"continue"				{ mkL KwContinue } <0,ppSC>	"default"				{ mkL KwDefault } <0,ppSC>	"do"					{ mkL KwDo } <0,ppSC>	"else"					{ mkL KwElse } <0,ppSC>	"enum"					{ mkL KwEnum }-<0,ppSC>	"error"					{ mkL KwError }-<0,ppSC>	"event"					{ mkL KwEvent } <0,ppSC>	"extern"				{ mkL KwExtern } <0,ppSC>	"for"					{ mkL KwFor } <0,ppSC>	"goto"					{ mkL KwGoto } <0,ppSC>	"if"					{ mkL KwIf }-<0,ppSC>	"namespace"				{ mkL KwNamespace } <0,ppSC>	"return"				{ mkL KwReturn } <0,ppSC>	"sizeof"				{ mkL KwSizeof } <0,ppSC>	"static"				{ mkL KwStatic } <0,ppSC>	"static_assert"				{ mkL KwStaticAssert } <0,ppSC>	"struct"				{ mkL KwStruct } <0,ppSC>	"switch"				{ mkL KwSwitch }-<0,ppSC>	"this"					{ mkL KwThis } <0,ppSC>	"typedef"				{ mkL KwTypedef } <0,ppSC>	"union"					{ mkL KwUnion } <0,ppSC>	"void"					{ mkL KwVoid } <0,ppSC>	"while"					{ mkL KwWhile }-<0,ppSC>	"with"					{ mkL KwWith } <0,ppSC>	"bool"					{ mkL IdStdType } <0,ppSC>	"char"					{ mkL IdStdType } <0,ppSC>	"double"				{ mkL IdStdType }@@ -159,7 +152,6 @@ <0,ppSC>	"va_list"				{ mkL IdStdType } <0,ppSC>	"false"					{ mkL LitFalse } <0,ppSC>	"true"					{ mkL LitTrue }-<0,ppSC>	"`"[a-z]+				{ mkL IdTyVar } <0,ppSC>	"__func__"				{ mkL IdVar } <0,ppSC>	"__"[a-zA-Z]+"__"?			{ mkL IdConst } <0,ppSC>	[A-Z][A-Z0-9_]{1,2}			{ mkL IdSueType }
src/Language/Cimple/Parser.y view
@@ -3,9 +3,11 @@     ( parseTranslationUnit     ) where +import           Data.Fix               (Fix (..)) import           Language.Cimple.AST    (AssignOp (..), BinaryOp (..),                                          CommentStyle (..), LiteralType (..),-                                         Node (..), Scope (..), UnaryOp (..))+                                         Node, NodeF (..), Scope (..),+                                         UnaryOp (..)) import           Language.Cimple.Lexer  (Alex, AlexPosn (..), Lexeme (..),                                          alexError, alexMonadScan) import           Language.Cimple.Tokens (LexemeClass (..))@@ -26,38 +28,30 @@     ID_FUNC_TYPE		{ L _ IdFuncType		_ }     ID_STD_TYPE			{ L _ IdStdType			_ }     ID_SUE_TYPE			{ L _ IdSueType			_ }-    ID_TYVAR			{ L _ IdTyVar			_ }     ID_VAR			{ L _ IdVar			_ }-    bitmask			{ L _ KwBitmask			_ }     break			{ L _ KwBreak			_ }     case			{ L _ KwCase			_ }-    class			{ L _ KwClass			_ }     const			{ L _ KwConst			_ }     continue			{ L _ KwContinue		_ }     default			{ L _ KwDefault			_ }     do				{ L _ KwDo			_ }     else			{ L _ KwElse			_ }     enum			{ L _ KwEnum			_ }-    'error'			{ L _ KwError			_ }-    event			{ L _ KwEvent			_ }     extern			{ L _ KwExtern			_ }     for				{ L _ KwFor			_ }     goto			{ L _ KwGoto			_ }     if				{ L _ KwIf			_ }-    namespace			{ L _ KwNamespace		_ }     return			{ L _ KwReturn			_ }     sizeof			{ L _ KwSizeof			_ }     static			{ L _ KwStatic			_ }     static_assert		{ L _ KwStaticAssert		_ }     struct			{ L _ KwStruct			_ }     switch			{ L _ KwSwitch			_ }-    this			{ L _ KwThis			_ }     typedef			{ L _ KwTypedef			_ }     union			{ L _ KwUnion			_ }     VLA				{ L _ KwVla			_ }     void			{ L _ KwVoid			_ }     while			{ L _ KwWhile			_ }-    with			{ L _ KwWith			_ }     LIT_CHAR			{ L _ LitChar			_ }     LIT_FALSE			{ L _ LitFalse			_ }     LIT_TRUE			{ L _ LitTrue			_ }@@ -158,7 +152,7 @@  LicenseDecl :: { StringNode } LicenseDecl-:	'/*' 'License' CMT_WORD '\n' CopyrightDecls '*/'	{ LicenseDecl $3 $5 }+:	'/*' 'License' CMT_WORD '\n' CopyrightDecls '*/'	{ Fix $ LicenseDecl $3 (reverse $5) }  CopyrightDecls :: { [StringNode] } CopyrightDecls@@ -167,7 +161,7 @@  CopyrightDecl :: { StringNode } CopyrightDecl-:	' * ' 'Copyright' CopyrightDates CopyrightOwner '\n'	{ CopyrightDecl (fst $3) (snd $3) $4 }+:	' * ' 'Copyright' CopyrightDates CopyrightOwner '\n'	{ Fix $ CopyrightDecl (fst $3) (snd $3) $4 }  CopyrightDates :: { (StringLexeme, Maybe StringLexeme) } CopyrightDates@@ -189,11 +183,8 @@ |	Comment							{ $1 } |	ConstDecl						{ $1 } |	EnumDecl						{ $1 }-|	ErrorDecl						{ $1 }-|	Event							{ $1 } |	ExternC							{ $1 } |	FunctionDecl						{ $1 }-|	Namespace						{ $1 } |	PreprocDefine						{ $1 } |	PreprocIfdef(ToplevelDecls)				{ $1 } |	PreprocIf(ToplevelDecls)				{ $1 }@@ -204,57 +195,25 @@  StaticAssert :: { StringNode } StaticAssert-:	static_assert '(' ConstExpr ',' LIT_STRING ')' ';'	{ StaticAssert $3 $5 }--Namespace :: { StringNode }-Namespace-:	NamespaceDeclarator					{ $1 Global }-|	static NamespaceDeclarator				{ $2 Static }--NamespaceDeclarator :: { Scope -> StringNode }-NamespaceDeclarator-:	class ID_SUE_TYPE TypeParams '{' ToplevelDecls '}'	{ \s -> Class s $2 $3 (reverse $5) }-|	namespace IdVar '{' ToplevelDecls '}'			{ \s -> Namespace s $2 (reverse $4) }--TypeParams :: { [StringNode] }-TypeParams-:								{ [] }-|	'<' ID_TYVAR '>'					{ [TyVar $2] }--Event :: { StringNode }-Event-:	event IdVar       '{' Comment EventType '}'		{ Event $2 (Commented $4 $5) }-|	event IdVar const '{' Comment EventType '}'		{ Event $2 (Commented $5 $6) }--EventType :: { StringNode }-EventType-:	typedef void EventParams ';'				{ $3 }--EventParams :: { StringNode }-EventParams-:	FunctionParamList					{ EventParams $1 }--ErrorDecl :: { StringNode }-ErrorDecl-:	'error' for IdVar EnumeratorList			{ ErrorDecl $3 $4 }+:	static_assert '(' ConstExpr ',' LIT_STRING ')' ';'	{ Fix $ StaticAssert $3 $5 }  Comment :: { StringNode } Comment-:	'/*' CommentTokens '*/'					{ Comment Regular $1 (reverse $2) $3 }-|	'/**' CommentTokens '*/'				{ Comment Doxygen $1 (reverse $2) $3 }-|	'/***' CommentTokens '*/'				{ Comment Block $1 (reverse $2) $3 }-|	'/**/'							{ CommentBlock $1 }+:	'/*' CommentTokens '*/'					{ Fix $ Comment Regular $1 (reverse $2) $3 }+|	'/**' CommentTokens '*/'				{ Fix $ Comment Doxygen $1 (reverse $2) $3 }+|	'/***' CommentTokens '*/'				{ Fix $ Comment Block $1 (reverse $2) $3 }+|	'/**/'							{ Fix $ CommentBlock $1 } -CommentTokens :: { [StringNode] }+CommentTokens :: { [StringLexeme] } CommentTokens :	CommentToken						{ [$1] } |	CommentTokens CommentToken				{ $2 : $1 } -CommentToken :: { StringNode }+CommentToken :: { StringLexeme } CommentToken-:	CommentWord						{ CommentWord $1 }-|	'\n'							{ CommentWord $1 }-|	' * '							{ CommentWord $1 }+:	CommentWord						{ $1 }+|	'\n'							{ $1 }+|	' * '							{ $1 }  CommentWords :: { [StringLexeme] } CommentWords@@ -284,42 +243,42 @@ |	'='							{ $1 }  PreprocIfdef(decls)-:	'#ifdef' ID_CONST decls PreprocElse(decls) '#endif'	{ PreprocIfdef $2 (reverse $3) $4 }-|	'#ifndef' ID_CONST decls PreprocElse(decls) '#endif'	{ PreprocIfndef $2 (reverse $3) $4 }+:	'#ifdef' ID_CONST decls PreprocElse(decls) '#endif'	{ Fix $ PreprocIfdef $2 (reverse $3) $4 }+|	'#ifndef' ID_CONST decls PreprocElse(decls) '#endif'	{ Fix $ PreprocIfndef $2 (reverse $3) $4 }  PreprocIf(decls)-:	'#if' PreprocConstExpr '\n' decls PreprocElse(decls) '#endif'	{ PreprocIf $2 (reverse $4) $5 }+:	'#if' PreprocConstExpr '\n' decls PreprocElse(decls) '#endif'	{ Fix $ PreprocIf $2 (reverse $4) $5 }  PreprocElse(decls)-:								{ PreprocElse [] }-|	'#else' decls						{ PreprocElse $2 }-|	'#elif' PreprocConstExpr '\n' decls PreprocElse(decls)	{ PreprocElif $2 (reverse $4) $5 }+:								{ Fix $ PreprocElse [] }+|	'#else' decls						{ Fix $ PreprocElse (reverse $2) }+|	'#elif' PreprocConstExpr '\n' decls PreprocElse(decls)	{ Fix $ PreprocElif $2 (reverse $4) $5 }  PreprocInclude :: { StringNode } PreprocInclude-:	'#include' LIT_STRING					{ PreprocInclude $2 }-|	'#include' LIT_SYS_INCLUDE				{ PreprocInclude $2 }+:	'#include' LIT_STRING					{ Fix $ PreprocInclude $2 }+|	'#include' LIT_SYS_INCLUDE				{ Fix $ PreprocInclude $2 }  PreprocDefine :: { StringNode } PreprocDefine-:	'#define' ID_CONST '\n'					{ PreprocDefine $2 }-|	'#define' ID_CONST PreprocSafeExpr(ConstExpr) '\n'	{ PreprocDefineConst $2 $3 }-|	'#define' ID_CONST MacroParamList MacroBody '\n'	{ PreprocDefineMacro $2 $3 $4 }+:	'#define' ID_CONST '\n'					{ Fix $ PreprocDefine $2 }+|	'#define' ID_CONST PreprocSafeExpr(ConstExpr) '\n'	{ Fix $ PreprocDefineConst $2 $3 }+|	'#define' ID_CONST MacroParamList MacroBody '\n'	{ Fix $ PreprocDefineMacro $2 $3 $4 }  PreprocUndef :: { StringNode } PreprocUndef-:	'#undef' ID_CONST					{ PreprocUndef $2 }+:	'#undef' ID_CONST					{ Fix $ PreprocUndef $2 }  PreprocConstExpr :: { StringNode } PreprocConstExpr :	PureExpr(PreprocConstExpr)				{ $1 }-|	'defined' '(' ID_CONST ')'				{ PreprocDefined $3 }+|	'defined' '(' ID_CONST ')'				{ Fix $ PreprocDefined $3 }  MacroParamList :: { [StringNode] } MacroParamList :	'(' ')'							{ [] } |	'(' MacroParams ')'					{ reverse $2 }-|	'(' MacroParams ',' '...' ')'				{ reverse $ Ellipsis : $2 }+|	'(' MacroParams ',' '...' ')'				{ reverse $ Fix Ellipsis : $2 }  MacroParams :: { [StringNode] } MacroParams@@ -328,12 +287,12 @@  MacroParam :: { StringNode } MacroParam-:	IdVar							{ MacroParam $1 }+:	IdVar							{ Fix $ MacroParam $1 }  MacroBody :: { StringNode } MacroBody :	do CompoundStmt while '(' LIT_INTEGER ')'		{% macroBodyStmt $2 $5 }-|	FunctionCall						{ MacroBodyFunCall $1 }+|	FunctionCall						{ Fix $ MacroBodyFunCall $1 }  ExternC :: { StringNode } ExternC@@ -354,10 +313,9 @@ Stmt :	PreprocIfdef(Stmts)					{ $1 } |	PreprocIf(Stmts)					{ $1 }-|	PreprocDefine Stmts PreprocUndef			{ PreprocScopedDefine $1 $2 $3 }-|	LabelStmt						{ $1 }+|	PreprocDefine Stmts PreprocUndef			{ Fix $ PreprocScopedDefine $1 $2 $3 } |	DeclStmt						{ $1 }-|	CompoundStmt						{ CompoundStmt $1 }+|	CompoundStmt						{ $1 } |	IfStmt							{ $1 } |	ForStmt							{ $1 } |	WhileStmt						{ $1 }@@ -365,23 +323,24 @@ |	AssignExpr ';'						{ $1 } |	ExprStmt ';'						{ $1 } |	FunctionCall ';'					{ $1 }-|	break ';'						{ Break }-|	goto ID_CONST ';'					{ Goto $2 }-|	continue ';'						{ Continue }-|	return ';'						{ Return Nothing }-|	return Expr ';'						{ Return (Just $2) }-|	switch '(' Expr ')' CompoundStmt			{ SwitchStmt $3 $5 }+|	break ';'						{ Fix $ Break }+|	goto ID_CONST ';'					{ Fix $ Goto $2 }+|	ID_CONST ':' Stmt					{ Fix $ Label $1 $3 }+|	continue ';'						{ Fix $ Continue }+|	return ';'						{ Fix $ Return Nothing }+|	return Expr ';'						{ Fix $ Return (Just $2) }+|	switch '(' Expr ')' '{' SwitchCases '}'			{ Fix $ SwitchStmt $3 (reverse $6) } |	Comment							{ $1 }  IfStmt :: { StringNode } IfStmt-:	if '(' Expr ')' CompoundStmt				{ IfStmt $3 $5 Nothing }-|	if '(' Expr ')' CompoundStmt else IfStmt		{ IfStmt $3 $5 (Just $7) }-|	if '(' Expr ')' CompoundStmt else CompoundStmt		{ IfStmt $3 $5 (Just (CompoundStmt $7)) }+:	if '(' Expr ')' CompoundStmt				{ Fix $ IfStmt $3 $5 Nothing }+|	if '(' Expr ')' CompoundStmt else IfStmt		{ Fix $ IfStmt $3 $5 (Just $7) }+|	if '(' Expr ')' CompoundStmt else CompoundStmt		{ Fix $ IfStmt $3 $5 (Just $7) }  ForStmt :: { StringNode } ForStmt-:	for '(' ForInit Expr ';' ForNext ')' CompoundStmt	{ ForStmt $3 $4 $6 $8 }+:	for '(' ForInit Expr ';' ForNext ')' CompoundStmt	{ Fix $ ForStmt $3 $4 $6 $8 }  ForInit :: { StringNode } ForInit@@ -395,54 +354,57 @@  WhileStmt :: { StringNode } WhileStmt-:	while '(' Expr ')' CompoundStmt				{ WhileStmt $3 $5 }+:	while '(' Expr ')' CompoundStmt				{ Fix $ WhileStmt $3 $5 }  DoWhileStmt :: { StringNode } DoWhileStmt-:	do CompoundStmt while '(' Expr ')' ';'			{ DoWhileStmt $2 $5 }+:	do CompoundStmt while '(' Expr ')' ';'			{ Fix $ DoWhileStmt $2 $5 } -LabelStmt :: { StringNode }-LabelStmt-:	case Expr ':' AfterLabelStmt				{ Case $2 $4 }-|	default ':' AfterLabelStmt				{ Default $3 }-|	ID_CONST ':' Stmt					{ Label $1 $3 }+SwitchCases :: { [StringNode] }+SwitchCases+:	SwitchCase						{ [$1] }+|	SwitchCases SwitchCase					{ $2 : $1 } -AfterLabelStmt :: { StringNode }-AfterLabelStmt-:	CompoundStmt						{ CompoundStmt $1 }-|	LabelStmt						{ $1 }-|	return Expr ';'						{ Return (Just $2) }+SwitchCase :: { StringNode }+SwitchCase+:	case Expr ':' SwitchCaseBody				{ Fix $ Case $2 $4 }+|	default ':' SwitchCaseBody				{ Fix $ Default $3 } +SwitchCaseBody :: { StringNode }+SwitchCaseBody+:	CompoundStmt						{ $1 }+|	SwitchCase						{ $1 }+|	return Expr ';'						{ Fix $ Return (Just $2) }+ DeclStmt :: { StringNode } DeclStmt :	VarDecl							{ $1 }-|	VLA '(' QualType ',' IdVar ',' Expr ')' ';'		{ VLA $3 $5 $7 }+|	VLA '(' QualType ',' IdVar ',' Expr ')' ';'		{ Fix $ VLA $3 $5 $7 }  VarDecl :: { StringNode } VarDecl-:	QualType Declarator ';'					{ VarDecl $1 $2 }+:	QualType Declarator ';'					{ Fix $ VarDecl $1 $2 }  Declarator :: { StringNode } Declarator-:	DeclSpec '=' InitialiserExpr				{ Declarator $1 (Just $3) }-|	DeclSpec						{ Declarator $1 Nothing }+:	DeclSpec '=' InitialiserExpr				{ Fix $ Declarator $1 (Just $3) }+|	DeclSpec						{ Fix $ Declarator $1 Nothing }  InitialiserExpr :: { StringNode } InitialiserExpr-:	InitialiserList						{ InitialiserList $1 }+:	InitialiserList						{ Fix $ InitialiserList $1 } |	Expr							{ $1 }  DeclSpec :: { StringNode } DeclSpec-:	IdVar							{ DeclSpecVar $1 }-|	DeclSpec '[' ']'					{ DeclSpecArray $1 Nothing }-|	DeclSpec '[' Expr ']'					{ DeclSpecArray $1 (Just $3) }+:	IdVar							{ Fix $ DeclSpecVar $1 }+|	DeclSpec '[' ']'					{ Fix $ DeclSpecArray $1 Nothing }+|	DeclSpec '[' Expr ']'					{ Fix $ DeclSpecArray $1 (Just $3) }  IdVar :: { Lexeme String } IdVar :	ID_VAR							{ $1 } |	default							{ $1 }-|	'error'							{ $1 }  InitialiserList :: { [StringNode] } InitialiserList@@ -457,19 +419,19 @@ Initialiser :: { StringNode } Initialiser :	Expr							{ $1 }-|	InitialiserList						{ InitialiserList $1 }+|	InitialiserList						{ Fix $ InitialiserList $1 } -CompoundStmt :: { [StringNode] }+CompoundStmt :: { StringNode } CompoundStmt-:	'{' Stmts '}'						{ reverse $2 }+:	'{' Stmts '}'						{ Fix $ CompoundStmt (reverse $2) }  -- Expressions that are safe for use as macro body without () around it.. PreprocSafeExpr(x) :	LiteralExpr						{ $1 }-|	'(' x ')'						{ ParenExpr $2 }-|	'(' QualType ')' x %prec CAST				{ CastExpr $2 $4 }-|	sizeof '(' x ')'					{ SizeofExpr $3 }-|	sizeof '(' QualType ')'					{ SizeofType $3 }+|	'(' x ')'						{ Fix $ ParenExpr $2 }+|	'(' QualType ')' x %prec CAST				{ Fix $ CastExpr $2 $4 }+|	sizeof '(' x ')'					{ Fix $ SizeofExpr $3 }+|	sizeof '(' QualType ')'					{ Fix $ SizeofType $3 }  ConstExpr :: { StringNode } ConstExpr@@ -477,51 +439,51 @@  PureExpr(x) :	PreprocSafeExpr(x)					{ $1 }-|	x '!=' x						{ BinaryExpr $1 BopNe $3 }-|	x '==' x						{ BinaryExpr $1 BopEq $3 }-|	x '||' x						{ BinaryExpr $1 BopOr $3 }-|	x '^' x							{ BinaryExpr $1 BopBitXor $3 }-|	x '|' x							{ BinaryExpr $1 BopBitOr $3 }-|	x '&&' x						{ BinaryExpr $1 BopAnd $3 }-|	x '&' x							{ BinaryExpr $1 BopBitAnd $3 }-|	x '/' x							{ BinaryExpr $1 BopDiv $3 }-|	x '*' x							{ BinaryExpr $1 BopMul $3 }-|	x '%' x							{ BinaryExpr $1 BopMod $3 }-|	x '+' x							{ BinaryExpr $1 BopPlus $3 }-|	x '-' x							{ BinaryExpr $1 BopMinus $3 }-|	x '<' x							{ BinaryExpr $1 BopLt $3 }-|	x '<=' x						{ BinaryExpr $1 BopLe $3 }-|	x '<<' x						{ BinaryExpr $1 BopLsh $3 }-|	x '>' x							{ BinaryExpr $1 BopGt $3 }-|	x '>=' x						{ BinaryExpr $1 BopGe $3 }-|	x '>>' x						{ BinaryExpr $1 BopRsh $3 }-|	x '?' x ':' x						{ TernaryExpr $1 $3 $5 }-|	'!' x							{ UnaryExpr UopNot $2 }-|	'~' x							{ UnaryExpr UopNeg $2 }-|	'-' x %prec NEG						{ UnaryExpr UopMinus $2 }-|	'&' x %prec ADDRESS					{ UnaryExpr UopAddress $2 }+|	x '!=' x						{ Fix $ BinaryExpr $1 BopNe $3 }+|	x '==' x						{ Fix $ BinaryExpr $1 BopEq $3 }+|	x '||' x						{ Fix $ BinaryExpr $1 BopOr $3 }+|	x '^' x							{ Fix $ BinaryExpr $1 BopBitXor $3 }+|	x '|' x							{ Fix $ BinaryExpr $1 BopBitOr $3 }+|	x '&&' x						{ Fix $ BinaryExpr $1 BopAnd $3 }+|	x '&' x							{ Fix $ BinaryExpr $1 BopBitAnd $3 }+|	x '/' x							{ Fix $ BinaryExpr $1 BopDiv $3 }+|	x '*' x							{ Fix $ BinaryExpr $1 BopMul $3 }+|	x '%' x							{ Fix $ BinaryExpr $1 BopMod $3 }+|	x '+' x							{ Fix $ BinaryExpr $1 BopPlus $3 }+|	x '-' x							{ Fix $ BinaryExpr $1 BopMinus $3 }+|	x '<' x							{ Fix $ BinaryExpr $1 BopLt $3 }+|	x '<=' x						{ Fix $ BinaryExpr $1 BopLe $3 }+|	x '<<' x						{ Fix $ BinaryExpr $1 BopLsh $3 }+|	x '>' x							{ Fix $ BinaryExpr $1 BopGt $3 }+|	x '>=' x						{ Fix $ BinaryExpr $1 BopGe $3 }+|	x '>>' x						{ Fix $ BinaryExpr $1 BopRsh $3 }+|	x '?' x ':' x						{ Fix $ TernaryExpr $1 $3 $5 }+|	'!' x							{ Fix $ UnaryExpr UopNot $2 }+|	'~' x							{ Fix $ UnaryExpr UopNeg $2 }+|	'-' x %prec NEG						{ Fix $ UnaryExpr UopMinus $2 }+|	'&' x %prec ADDRESS					{ Fix $ UnaryExpr UopAddress $2 }  LiteralExpr :: { StringNode } LiteralExpr :	StringLiteralExpr					{ $1 }-|	LIT_CHAR						{ LiteralExpr Char $1 }-|	LIT_INTEGER						{ LiteralExpr Int $1 }-|	LIT_FALSE						{ LiteralExpr Bool $1 }-|	LIT_TRUE						{ LiteralExpr Bool $1 }-|	ID_CONST						{ LiteralExpr ConstId $1 }+|	LIT_CHAR						{ Fix $ LiteralExpr Char $1 }+|	LIT_INTEGER						{ Fix $ LiteralExpr Int $1 }+|	LIT_FALSE						{ Fix $ LiteralExpr Bool $1 }+|	LIT_TRUE						{ Fix $ LiteralExpr Bool $1 }+|	ID_CONST						{ Fix $ LiteralExpr ConstId $1 }  StringLiteralExpr :: { StringNode } StringLiteralExpr-:	LIT_STRING						{ LiteralExpr String $1 }+:	LIT_STRING						{ Fix $ LiteralExpr String $1 } |	StringLiteralExpr LIT_STRING				{ $1 }  LhsExpr :: { StringNode } LhsExpr-:	IdVar							{ VarExpr $1 }-|	'*' LhsExpr %prec DEREF					{ UnaryExpr UopDeref $2 }-|	LhsExpr '.' IdVar					{ MemberAccess $1 $3 }-|	LhsExpr '->' IdVar					{ PointerAccess $1 $3 }-|	LhsExpr '[' Expr ']'					{ ArrayAccess $1 $3 }+:	IdVar							{ Fix $ VarExpr $1 }+|	'*' LhsExpr %prec DEREF					{ Fix $ UnaryExpr UopDeref $2 }+|	LhsExpr '.' IdVar					{ Fix $ MemberAccess $1 $3 }+|	LhsExpr '->' IdVar					{ Fix $ PointerAccess $1 $3 }+|	LhsExpr '[' Expr ']'					{ Fix $ ArrayAccess $1 $3 }  Expr :: { StringNode } Expr@@ -534,11 +496,11 @@ -- Allow `(Type){0}` to set struct values to all-zero. CompoundExpr :: { StringNode } CompoundExpr-:	'(' QualType ')' '{' Expr '}'				{ CompoundExpr $2 $5 }+:	'(' QualType ')' '{' Expr '}'				{ Fix $ CompoundExpr $2 $5 }  AssignExpr :: { StringNode } AssignExpr-:	LhsExpr AssignOperator Expr				{ AssignExpr $1 $2 $3 }+:	LhsExpr AssignOperator Expr				{ Fix $ AssignExpr $1 $2 $3 }  AssignOperator :: { AssignOp } AssignOperator@@ -556,12 +518,12 @@  ExprStmt :: { StringNode } ExprStmt-:	'++' Expr						{ UnaryExpr UopIncr $2 }-|	'--' Expr						{ UnaryExpr UopDecr $2 }+:	'++' Expr						{ Fix $ UnaryExpr UopIncr $2 }+|	'--' Expr						{ Fix $ UnaryExpr UopDecr $2 }  FunctionCall :: { StringNode } FunctionCall-:	Expr ArgList						{ FunctionCall $1 $2 }+:	Expr ArgList						{ Fix $ FunctionCall $1 $2 }  ArgList :: { [StringNode] } ArgList@@ -576,15 +538,13 @@ Arg :: { StringNode } Arg :	Expr							{ $1 }-|	Comment Expr						{ CommentExpr $1 $2 }+|	Comment Expr						{ Fix $ CommentExpr $1 $2 }  EnumDecl :: { StringNode } EnumDecl-:	enum class ID_SUE_TYPE EnumeratorList			{ EnumClass $3 $4 }-|	enum       ID_SUE_TYPE EnumeratorList ';'		{ EnumConsts (Just $2) $3 }-|	enum                   EnumeratorList ';'		{ EnumConsts Nothing $2 }-|	typedef enum ID_SUE_TYPE EnumeratorList ID_SUE_TYPE ';'	{ EnumDecl $3 $4 $5 }-|	bitmask ID_SUE_TYPE EnumeratorList			{ EnumDecl $2 $3 $2 }+:	enum ID_SUE_TYPE EnumeratorList ';'			{ Fix $ EnumConsts (Just $2) $3 }+|	enum             EnumeratorList ';'			{ Fix $ EnumConsts Nothing $2 }+|	typedef enum ID_SUE_TYPE EnumeratorList ID_SUE_TYPE ';'	{ Fix $ EnumDecl $3 $4 $5 }  EnumeratorList :: { [StringNode] } EnumeratorList@@ -597,9 +557,8 @@  Enumerator :: { StringNode } Enumerator-:	EnumeratorName ','					{ Enumerator $1 Nothing }-|	EnumeratorName '=' ConstExpr ','			{ Enumerator $1 (Just $3) }-|	namespace ID_CONST '{' Enumerators '}'			{ Namespace Global $2 $4 }+:	EnumeratorName ','					{ Fix $ Enumerator $1 Nothing }+|	EnumeratorName '=' ConstExpr ','			{ Fix $ Enumerator $1 (Just $3) } |	Comment							{ $1 }  EnumeratorName :: { Lexeme String }@@ -610,14 +569,12 @@ AggregateDecl :: { StringNode } AggregateDecl :	AggregateType ';'					{ $1 }-|	class ID_SUE_TYPE TypeParams ';'			{ ClassForward $2 $3 }-|	typedef AggregateType ID_SUE_TYPE ';'			{ Typedef $2 $3 }+|	typedef AggregateType ID_SUE_TYPE ';'			{ Fix $ Typedef $2 $3 }  AggregateType :: { StringNode } AggregateType-:	struct ID_SUE_TYPE '{' MemberDeclList '}'		{ Struct $2 $4 }-|	struct this '{' MemberDeclList '}'			{ Struct $2 $4 }-|	union ID_SUE_TYPE '{' MemberDeclList '}'		{ Union $2 $4 }+:	struct ID_SUE_TYPE '{' MemberDeclList '}'		{ Fix $ Struct $2 $4 }+|	union ID_SUE_TYPE '{' MemberDeclList '}'		{ Fix $ Union $2 $4 }  MemberDeclList :: { [StringNode] } MemberDeclList@@ -630,42 +587,39 @@  MemberDecl :: { StringNode } MemberDecl-:	QualType DeclSpec ';'					{ MemberDecl $1 $2 Nothing }-|	QualType DeclSpec ':' LIT_INTEGER ';'			{ MemberDecl $1 $2 (Just $4) }-|	namespace IdVar '{' MemberDeclList '}'			{ Namespace Global $2 $4 }+:	QualType DeclSpec ';'					{ Fix $ MemberDecl $1 $2 Nothing }+|	QualType DeclSpec ':' LIT_INTEGER ';'			{ Fix $ MemberDecl $1 $2 (Just $4) } |	PreprocIfdef(MemberDeclList)				{ $1 } |	Comment							{ $1 }  TypedefDecl :: { StringNode } TypedefDecl-:	typedef QualType ID_SUE_TYPE ';'			{ Typedef $2 $3 }-|	typedef FunctionPrototype(ID_FUNC_TYPE) ';'		{ TypedefFunction $2 }+:	typedef QualType ID_SUE_TYPE ';'			{ Fix $ Typedef $2 $3 }+|	typedef FunctionPrototype(ID_FUNC_TYPE) ';'		{ Fix $ TypedefFunction $2 }  QualType :: { StringNode } QualType :	LeafType						{                               $1 }-|	LeafType '*'						{                     TyPointer $1 }-|	LeafType '*' '*'					{ TyPointer          (TyPointer $1) }-|	LeafType '*' const					{            TyConst (TyPointer $1) }-|	LeafType '*' const '*'					{ TyPointer (TyConst (TyPointer $1)) }-|	LeafType const						{                                TyConst $1 }-|	LeafType const '*'					{                     TyPointer (TyConst $1) }-|	LeafType const '*' const				{            TyConst (TyPointer (TyConst $1)) }-|	LeafType const '*' const '*'				{ TyPointer (TyConst (TyPointer (TyConst $1))) }-|	const LeafType						{                                TyConst $2 }-|	const LeafType '*'					{                     TyPointer (TyConst $2) }-|	const LeafType '*' const				{            TyConst (TyPointer (TyConst $2)) }-|	const LeafType '*' const '*'				{ TyPointer (TyConst (TyPointer (TyConst $2))) }+|	LeafType '*'						{                     tyPointer $1 }+|	LeafType '*' '*'					{ tyPointer          (tyPointer $1) }+|	LeafType '*' const					{            tyConst (tyPointer $1) }+|	LeafType '*' const '*'					{ tyPointer (tyConst (tyPointer $1)) }+|	LeafType const						{                                tyConst $1 }+|	LeafType const '*'					{                     tyPointer (tyConst $1) }+|	LeafType const '*' const				{            tyConst (tyPointer (tyConst $1)) }+|	LeafType const '*' const '*'				{ tyPointer (tyConst (tyPointer (tyConst $1))) }+|	const LeafType						{                                tyConst $2 }+|	const LeafType '*'					{                     tyPointer (tyConst $2) }+|	const LeafType '*' const				{            tyConst (tyPointer (tyConst $2)) }+|	const LeafType '*' const '*'				{ tyPointer (tyConst (tyPointer (tyConst $2))) }  LeafType :: { StringNode } LeafType-:	struct ID_SUE_TYPE					{ TyStruct $2 }-|	void							{ TyStd $1 }-|	this							{ TyStd $1 }-|	ID_FUNC_TYPE						{ TyFunc $1 }-|	ID_STD_TYPE						{ TyStd $1 }-|	ID_SUE_TYPE						{ TyUserDefined $1 }-|	ID_TYVAR						{ TyVar $1 }+:	struct ID_SUE_TYPE					{ Fix $ TyStruct $2 }+|	void							{ Fix $ TyStd $1 }+|	ID_FUNC_TYPE						{ Fix $ TyFunc $1 }+|	ID_STD_TYPE						{ Fix $ TyStd $1 }+|	ID_SUE_TYPE						{ Fix $ TyUserDefined $1 }  FunctionDecl :: { StringNode } FunctionDecl@@ -674,36 +628,19 @@  FunctionDeclarator :: { Scope -> StringNode } FunctionDeclarator-:	FunctionPrototype(IdVar) WithError			{ \s -> FunctionDecl s $1 $2 }-|	FunctionPrototype(IdVar) CompoundStmt			{ \s -> FunctionDefn s $1 $2 }-|	QualType DeclSpec '{' Accessors '}'			{ \s -> Property $1 $2 (reverse $4) }--Accessors :: { [StringNode] }-Accessors-:	Accessor						{ [$1] }-|	Accessors Accessor					{ $2 : $1 }--Accessor :: { StringNode }-Accessor-:	IdVar FunctionParamList WithError			{ Accessor $1 $2 $3 }-|	Comment							{ $1 }--WithError :: { Maybe StringNode }-WithError-:	';'							{ Nothing }-|	with 'error' EnumeratorList				{ Just (ErrorList $3) }-|	with 'error' for IdVar ';'				{ Just (ErrorFor $4) }+:	FunctionPrototype(IdVar) ';'				{ \s -> Fix $ FunctionDecl s $1 }+|	FunctionPrototype(IdVar) CompoundStmt			{ \s -> Fix $ FunctionDefn s $1 $2 }  FunctionPrototype(id)-:	QualType id FunctionParamList				{ FunctionPrototype $1 $2 $3 }-|	QualType id FunctionParamList const			{ FunctionPrototype $1 $2 $3 }+:	QualType id FunctionParamList				{ Fix $ FunctionPrototype $1 $2 $3 }+|	QualType id FunctionParamList const			{ Fix $ FunctionPrototype $1 $2 $3 }  FunctionParamList :: { [StringNode] } FunctionParamList :	'(' ')'							{ [] }-|	'(' void ')'						{ [TyStd $2] }+|	'(' void ')'						{ [Fix $ TyStd $2] } |	'(' FunctionParams ')'					{ reverse $2 }-|	'(' FunctionParams ',' '...' ')'			{ reverse $ Ellipsis : $2 }+|	'(' FunctionParams ',' '...' ')'			{ reverse $ Fix Ellipsis : $2 }  FunctionParams :: { [StringNode] } FunctionParams@@ -712,18 +649,22 @@  FunctionParam :: { StringNode } FunctionParam-:	QualType DeclSpec					{ FunctionParam $1 $2 }+:	QualType DeclSpec					{ Fix $ FunctionParam $1 $2 }  ConstDecl :: { StringNode } ConstDecl-:	extern const LeafType ID_VAR ';'			{ ConstDecl $3 $4 }-|	const LeafType ID_VAR '=' InitialiserExpr ';'		{ ConstDefn Global $2 $3 $5 }-|	static const LeafType ID_VAR '=' InitialiserExpr ';'	{ ConstDefn Static $3 $4 $6 }+:	extern const LeafType ID_VAR ';'			{ Fix $ ConstDecl $3 $4 }+|	const LeafType ID_VAR '=' InitialiserExpr ';'		{ Fix $ ConstDefn Global $2 $3 $5 }+|	static const LeafType ID_VAR '=' InitialiserExpr ';'	{ Fix $ ConstDefn Static $3 $4 $6 }  { type StringLexeme = Lexeme String-type StringNode = Node () StringLexeme+type StringNode = Node StringLexeme +tyPointer, tyConst :: StringNode -> StringNode+tyPointer = Fix . TyPointer+tyConst = Fix . TyConst+ parseError :: Show text => (Lexeme text, [String]) -> Alex a parseError (L (AlexPn _ line col) c t, options) =     alexError $ show line <> ":" <> show col <> ": Parse error near " <> show c <> ": "@@ -739,17 +680,17 @@     -> Lexeme String     -> Alex StringNode externC (L _ _ "__cplusplus") (L _ _ "\"C\"") decls (L _ _ "__cplusplus") =-    return $ ExternC decls+    return $ Fix $ ExternC decls externC _ lang _ _ =     alexError $ show lang         <> ": extern \"C\" declaration invalid (did you spell __cplusplus right?)"  macroBodyStmt-    :: [StringNode]+    :: StringNode     -> Lexeme String     -> Alex StringNode macroBodyStmt decls (L _ _ "0") =-    return $ MacroBodyStmt decls+    return $ Fix $ MacroBodyStmt decls macroBodyStmt _ cond =     alexError $ show cond         <> ": macro do-while body must end in 'while (0)'"
src/Language/Cimple/Pretty.hs view
@@ -1,99 +1,70 @@+{-# LANGUAGE LambdaCase    #-}+{-# LANGUAGE TupleSections #-} module Language.Cimple.Pretty (ppTranslationUnit) where +import           Data.Fix                     (foldFix) import qualified Data.List                    as List import           Data.Text                    (Text) import qualified Data.Text                    as Text import           Language.Cimple              (AssignOp (..), BinaryOp (..),                                                CommentStyle (..), Lexeme (..),-                                               LexemeClass (..), Node (..),-                                               Scope (..), UnaryOp (..),-                                               lexemeText)+                                               LexemeClass (..), Node,+                                               NodeF (..), Scope (..),+                                               UnaryOp (..), lexemeText) import           Prelude                      hiding ((<$>)) import           Text.Groom                   (groom)-import           Text.PrettyPrint.ANSI.Leijen+import           Text.PrettyPrint.ANSI.Leijen hiding (semi) +-- | Whether a node needs a semicolon at the end when it's a statement or+-- declaration.+data NeedsSemi+    = SemiNo+    | SemiYes++-- | Annotated Doc which is passed upwards through the fold. 'fst' is the+-- accumulated pretty-printed code. 'snd' states whether the current statement+-- should end in a semicolon ';'. E.g. function definitions don't, while+-- function declarations do.+type ADoc = (Doc, NeedsSemi)+bare, semi :: Doc -> ADoc+bare = (, SemiNo)+semi = (, SemiYes)++-- | Copy the 'NeedsSemi' from another 'ADoc' to a newly created doc.+cp :: ADoc -> Doc -> ADoc+cp (_, s) d = (d, s)+ ppText :: Text -> Doc ppText = text . Text.unpack  ppLexeme :: Lexeme Text -> Doc ppLexeme = ppText . lexemeText -ppCommaSep :: (a -> Doc) -> [a] -> Doc-ppCommaSep go = foldr (<>) empty . List.intersperse (text ", ") . map go--ppLineSep :: (a -> Doc) -> [a] -> Doc-ppLineSep go = foldr (<>) empty . List.intersperse linebreak . map go+ppSep :: Doc -> [ADoc] -> Doc+ppSep s = foldr (<>) empty . List.intersperse s . map fst -ppComment :: Show a => CommentStyle -> [Node a (Lexeme Text)] -> Doc-ppComment style cs =-    nest 1 (ppCommentStyle style <> ppCommentBody cs) <+> text "*/"+ppCommaSep :: [ADoc] -> Doc+ppCommaSep = ppSep (text ", ") -ppCommentStyle :: CommentStyle -> Doc-ppCommentStyle Block   = text "/***"-ppCommentStyle Doxygen = text "/**"-ppCommentStyle Regular = text "/*"+ppLineSep :: [ADoc] -> Doc+ppLineSep = ppSep linebreak -ppCommentWords :: [Lexeme Text] -> Doc-ppCommentWords = go+ppSemiSep :: [ADoc] -> Doc+ppSemiSep = ppEnd (char ';')   where-    go (L _ LitInteger t1 : L _ PctMinus m : L _ LitInteger t2 : xs) =-        space <> ppText t1 <> ppText m <> ppText t2 <> go xs-    go (L _ PctMinus m : L _ LitInteger t : xs) =-        space <> ppText m <> ppText t <> go xs--    go (l : L _ PctPeriod t : xs) = go [l] <> ppText t <> go xs-    go (l : L _ PctComma  t : xs) = go [l] <> ppText t <> go xs-    go (x                   : xs) = ppWord x <> go xs-    go []                         = empty--    ppWord (L _ CmtSpdxLicense   t) = space <> ppText t-    ppWord (L _ CmtSpdxCopyright t) = space <> ppText t-    ppWord (L _ CmtWord          t) = space <> ppText t-    ppWord (L _ CmtCode          t) = space <> ppText t-    ppWord (L _ CmtRef           t) = space <> ppText t-    ppWord (L _ CmtIndent        _) = char '*'-    ppWord (L _ PpNewline        _) = linebreak-    ppWord (L _ LitInteger       t) = space <> ppText t-    ppWord (L _ LitString        t) = space <> ppText t-    ppWord (L _ PctEMark         t) = space <> ppText t-    ppWord (L _ PctPlus          t) = space <> ppText t-    ppWord (L _ PctEq            t) = space <> ppText t-    ppWord (L _ PctMinus         t) = space <> ppText t-    ppWord (L _ PctPeriod        t) = space <> ppText t-    ppWord (L _ PctLParen        t) = space <> ppText t-    ppWord (L _ PctRParen        t) = space <> ppText t-    ppWord (L _ PctSemicolon     t) = space <> ppText t-    ppWord (L _ PctColon         t) = space <> ppText t-    ppWord (L _ PctQMark         t) = space <> ppText t-    ppWord (L _ PctSlash         t) = space <> ppText t-    ppWord (L _ PctGreater       t) = space <> ppText t-    ppWord (L _ PctLess          t) = space <> ppText t-    ppWord (L _ PctComma         t) = space <> ppText t-    ppWord x                        = error $ groom x+    ppEnd s = foldr (<>) empty . List.intersperse linebreak . map (addEnd s) -ppCommentBody :: Show a => [Node a (Lexeme Text)] -> Doc-ppCommentBody = ppCommentWords . map unCommentWord-  where-    unCommentWord (CommentWord l) = l-    unCommentWord x               = error $ groom x+    addEnd s (d, SemiYes) = d <> s+    addEnd _ (d, SemiNo)  = d  ppScope :: Scope -> Doc-ppScope Global = empty-ppScope Static = text "static "--ppType :: Show a => Node a (Lexeme Text) -> Doc-ppType (TyPointer     ty) = ppType ty <> char '*'-ppType (TyConst       ty) = ppType ty <+> text "const"-ppType (TyUserDefined l ) = ppLexeme l-ppType (TyStd         l ) = ppLexeme l-ppType (TyFunc        l ) = ppLexeme l-ppType (TyStruct      l ) = text "struct" <+> ppLexeme l-ppType (TyVar         l ) = ppLexeme l-ppType x                  = error . groom $ x+ppScope = \case+    Global -> empty+    Static -> text "static "  ppAssignOp :: AssignOp -> Doc-ppAssignOp op = case op of-    AopEq     -> text "="+ppAssignOp = \case+    AopEq     -> char '='     AopMul    -> text "*="     AopDiv    -> text "/="     AopPlus   -> text "+="@@ -106,7 +77,7 @@     AopRsh    -> text "<<="  ppBinaryOp :: BinaryOp -> Doc-ppBinaryOp op = case op of+ppBinaryOp = \case     BopNe     -> text "!="     BopEq     -> text "=="     BopOr     -> text "||"@@ -127,7 +98,7 @@     BopRsh    -> text ">>"  ppUnaryOp :: UnaryOp -> Doc-ppUnaryOp op = case op of+ppUnaryOp = \case     UopNot     -> char '!'     UopNeg     -> char '~'     UopMinus   -> char '-'@@ -136,458 +107,348 @@     UopIncr    -> text "++"     UopDecr    -> text "--" -ppInitialiserList :: Show a => [Node a (Lexeme Text)] -> Doc-ppInitialiserList l = char '{' <+> ppCommaSep ppExpr l <+> char '}'+ppCommentStyle :: CommentStyle -> Doc+ppCommentStyle = \case+    Block   -> text "/***"+    Doxygen -> text "/**"+    Regular -> text "/*" -ppDeclSpec :: Show a => Node a (Lexeme Text) -> Doc-ppDeclSpec (DeclSpecVar var        ) = ppLexeme var-ppDeclSpec (DeclSpecArray dspec dim) = ppDeclSpec dspec <> ppDim dim+ppCommentBody :: [Lexeme Text] -> Doc+ppCommentBody = go   where-    ppDim Nothing  = text "[]"-    ppDim (Just x) = char '[' <> ppExpr x <> char ']'-ppDeclSpec x = error $ groom x+    go (L _ LitInteger t1 : L _ PctMinus m : L _ LitInteger t2 : xs) =+        space <> ppText t1 <> ppText m <> ppText t2 <> go xs+    go (L _ PctMinus m : L _ LitInteger t : xs) =+        space <> ppText m <> ppText t <> go xs -ppDeclarator :: Show a => Node a (Lexeme Text) -> Doc-ppDeclarator (Declarator dspec Nothing) =-    ppDeclSpec dspec-ppDeclarator (Declarator dspec (Just initr)) =-    ppDeclSpec dspec <+> char '=' <+> ppExpr initr-ppDeclarator x = error $ groom x+    go (l : L _ PctPeriod t : xs) = go [l] <> ppText t <> go xs+    go (l : L _ PctComma  t : xs) = go [l] <> ppText t <> go xs+    go (x                   : xs) = ppWord x <> go xs+    go []                         = empty -ppFunctionParamList :: Show a => [Node a (Lexeme Text)] -> Doc-ppFunctionParamList xs = char '(' <> ppCommaSep go xs <> char ')'-  where-    go (TyStd l@(L _ KwVoid _)) = ppLexeme l-    go (FunctionParam ty dspec) = ppType ty <+> ppDeclSpec dspec-    go Ellipsis                 = text "..."-    go x                        = error $ groom x+    ppWord (L _ CmtSpdxLicense   t) = space <> ppText t+    ppWord (L _ CmtSpdxCopyright t) = space <> ppText t+    ppWord (L _ CmtWord          t) = space <> ppText t+    ppWord (L _ CmtCode          t) = space <> ppText t+    ppWord (L _ CmtRef           t) = space <> ppText t+    ppWord (L _ CmtIndent        _) = char '*'+    ppWord (L _ PpNewline        _) = linebreak+    ppWord (L _ LitInteger       t) = space <> ppText t+    ppWord (L _ LitString        t) = space <> ppText t+    ppWord (L _ PctEMark         t) = space <> ppText t+    ppWord (L _ PctPlus          t) = space <> ppText t+    ppWord (L _ PctEq            t) = space <> ppText t+    ppWord (L _ PctMinus         t) = space <> ppText t+    ppWord (L _ PctPeriod        t) = space <> ppText t+    ppWord (L _ PctLParen        t) = space <> ppText t+    ppWord (L _ PctRParen        t) = space <> ppText t+    ppWord (L _ PctSemicolon     t) = space <> ppText t+    ppWord (L _ PctColon         t) = space <> ppText t+    ppWord (L _ PctQMark         t) = space <> ppText t+    ppWord (L _ PctSlash         t) = space <> ppText t+    ppWord (L _ PctGreater       t) = space <> ppText t+    ppWord (L _ PctLess          t) = space <> ppText t+    ppWord (L _ PctComma         t) = space <> ppText t+    ppWord x                        = error $ "ppWord: " <> groom x +ppComment :: CommentStyle -> [Lexeme Text] -> Doc+ppComment style cs =+    nest 1 (ppCommentStyle style <> ppCommentBody cs) <+> text "*/"++ppInitialiserList :: [ADoc] -> Doc+ppInitialiserList l = char '{' <+> ppCommaSep l <+> char '}'++ppFunctionParamList :: [ADoc] -> Doc+ppFunctionParamList xs = char '(' <> ppCommaSep xs <> char ')'+ ppFunctionPrototype-    :: Show a-    => Node a (Lexeme Text)+    :: ADoc     -> Lexeme Text-    -> [Node a (Lexeme Text)]+    -> [ADoc]     -> Doc ppFunctionPrototype ty name params =-    ppType ty <+> ppLexeme name <> ppFunctionParamList params--ppWithError :: Show a => Maybe (Node a (Lexeme Text)) -> Doc-ppWithError Nothing = char ';'-ppWithError (Just (ErrorFor name)) =-    text " with error for" <+> ppLexeme name <> char ';'-ppWithError (Just (ErrorList errs)) =-    nest 2 (-        text " with error" <+> char '{' <$>-        ppEnumeratorList errs-    ) <$> char '}'-ppWithError x = error $ groom x+    fst ty <+> ppLexeme name <> ppFunctionParamList params -ppFunctionCall :: Show a => Node a (Lexeme Text) -> [Node a (Lexeme Text)] -> Doc+ppFunctionCall :: ADoc -> [ADoc] -> Doc ppFunctionCall callee args =-    ppExpr callee <> char '(' <> ppCommaSep ppExpr args <> char ')'--ppMacroBody :: Show a => Node a (Lexeme Text) -> Doc-ppMacroBody (MacroBodyFunCall e@FunctionCall{}) = ppExpr e-ppMacroBody (MacroBodyStmt body) =-    nest 2 (-        text "do {" <$>-        ppStmtList body-    ) <$> text "} while (0)"-ppMacroBody x                                   = error $ groom x--ppMacroParam :: Show a => Node a (Lexeme Text) -> Doc-ppMacroParam (MacroParam l) = ppLexeme l-ppMacroParam Ellipsis       = text "..."-ppMacroParam x              = error $ groom x--ppMacroParamList :: Show a => [Node a (Lexeme Text)] -> Doc-ppMacroParamList xs = char '(' <> ppCommaSep ppMacroParam xs <> char ')'--ppNamespace :: ([a] -> Doc) -> Scope -> Lexeme Text -> [a] -> Doc-ppNamespace pp scope name members =-    nest 2 (-        ppScope scope <>-        text "namespace" <+> ppLexeme name <+> char '{' <$>-        pp members-    ) <$> char '}'--ppEnumerator :: Show a => Node a (Lexeme Text) -> Doc-ppEnumerator (Comment    style _ cs _ ) = ppComment style cs-ppEnumerator (Enumerator name  Nothing) = ppLexeme name <> char ','-ppEnumerator (Enumerator name (Just value)) =-    ppLexeme name <+> char '=' <+> ppExpr value <> char ','-ppEnumerator (Namespace scope name members) =-    ppNamespace ppEnumeratorList scope name members-ppEnumerator x = error $ groom x--ppEnumeratorList :: Show a => [Node a (Lexeme Text)] -> Doc-ppEnumeratorList = ppLineSep ppEnumerator--ppMemberDecl :: Show a => Node a (Lexeme Text) -> Doc-ppMemberDecl = ppDecl--ppMemberDeclList :: Show a => [Node a (Lexeme Text)] -> Doc-ppMemberDeclList = ppLineSep ppMemberDecl--ppAccessor :: Show a => Node a (Lexeme Text) -> Doc-ppAccessor (Comment style _ cs _) = ppComment style cs-ppAccessor (Accessor name params errs) =-    ppLexeme name <> ppFunctionParamList params <> ppWithError errs-ppAccessor x = error $ groom x--ppAccessorList :: Show a => [Node a (Lexeme Text)] -> Doc-ppAccessorList = ppLineSep ppAccessor--ppEventType :: Show a => Node a (Lexeme Text) -> Doc-ppEventType (Commented (Comment style _ cs _) ty) =-    ppComment style cs <$> ppEventType ty-ppEventType (EventParams params) =-    text "typedef void" <> ppFunctionParamList params-ppEventType x = error $ groom x--ppTypeParams :: Show a => [Node a (Lexeme Text)] -> Doc-ppTypeParams [] = empty-ppTypeParams xs = char '<' <> ppCommaSep pp xs <> char '>'-  where-    pp (TyVar x) = ppLexeme x-    pp x         = error $ groom x--ppCompoundStmt :: Show a => [Node a (Lexeme Text)] -> Doc-ppCompoundStmt body =-    nest 2 (-        char '{' <$>-        ppStmtList body-    ) <$> char '}'+    fst callee <> char '(' <> ppCommaSep args <> char ')' -ppStmtList :: Show a => [Node a (Lexeme Text)] -> Doc-ppStmtList = ppLineSep ppDecl+ppMacroParamList :: [ADoc] -> Doc+ppMacroParamList xs = char '(' <> ppCommaSep xs <> char ')'  ppIfStmt-    :: Show a-    => Node a (Lexeme Text)-    -> [Node a (Lexeme Text)]-    -> Maybe (Node a (Lexeme Text))+    :: ADoc+    -> ADoc+    -> Maybe ADoc     -> Doc ppIfStmt cond t Nothing =-    nest 2 (-        text "if (" <> ppExpr cond <> text ") {" <$>-        ppStmtList t-    ) <$> char '}'+    text "if (" <> fst cond <> text ")" <+> fst t ppIfStmt cond t (Just e) =-    nest 2 (-        text "if (" <> ppExpr cond <> text ") {" <$>-        ppStmtList t-    ) <$> nest 2 (char '}' <> text " else " <> ppDecl e)+    text "if (" <> fst cond <> text ")" <+> fst t <+> text "else" <+> fst e  ppForStmt-    :: Show a-    => Node a (Lexeme Text)-    -> Node a (Lexeme Text)-    -> Node a (Lexeme Text)-    -> [Node a (Lexeme Text)]+    :: ADoc+    -> ADoc+    -> ADoc+    -> ADoc     -> Doc ppForStmt i c n body =-    nest 2 (-        text "for ("-        <> ppDecl i-        <+> ppExpr c <> char ';'-        <+> ppExpr n-        <> text ") {" <$>-        ppStmtList body-    ) <$> char '}'+    text "for ("+    <> fst i <> char ';'+    <+> fst c <> char ';'+    <+> fst n+    <> char ')' <+>+    fst body  ppWhileStmt-    :: Show a-    => Node a (Lexeme Text)-    -> [Node a (Lexeme Text)]+    :: ADoc+    -> ADoc     -> Doc ppWhileStmt c body =-    nest 2 (-        text "while ("-        <> ppExpr c-        <> text ") {" <$>-        ppStmtList body-    ) <$> char '}'+    text "while ("+    <> fst c+    <> char ')' <+>+    fst body  ppDoWhileStmt-    :: Show a-    => [Node a (Lexeme Text)]-    -> Node a (Lexeme Text)+    :: ADoc+    -> ADoc     -> Doc ppDoWhileStmt body c =-    nest 2 (-        text "do ("-        <> text ") {" <$>-        ppStmtList body-    ) <$> text "} while (" <> ppExpr c <> char ')'+    text "do ("+    <> text ") {" <$>+    fst body+    <+> text "while (" <> fst c <> char ')'  ppSwitchStmt-    :: Show a-    => Node a (Lexeme Text)-    -> [Node a (Lexeme Text)]+    :: ADoc+    -> [ADoc]     -> Doc ppSwitchStmt c body =     nest 2 (         text "switch ("-        <> ppExpr c+        <> fst c         <> text ") {" <$>-        ppStmtList body+        ppSemiSep body     ) <$> char '}' -ppExpr :: Show a => Node a (Lexeme Text) -> Doc-ppExpr expr = case expr of-    -- Expressions-    VarExpr var       -> ppLexeme var-    LiteralExpr _ l   -> ppLexeme l-    SizeofExpr arg    -> text "sizeof(" <> ppExpr arg <> char ')'-    SizeofType arg    -> text "sizeof(" <> ppType arg <> char ')'-    BinaryExpr  l o r -> ppExpr l <+> ppBinaryOp o <+> ppExpr r-    AssignExpr  l o r -> ppExpr l <+> ppAssignOp o <+> ppExpr r-    TernaryExpr c t e -> ppTernaryExpr c t e-    UnaryExpr o e     -> ppUnaryOp o <> ppExpr e-    ParenExpr e       -> char '(' <> ppExpr e <> char ')'-    FunctionCall c  a -> ppFunctionCall c a-    ArrayAccess  e  i -> ppExpr e <> char '[' <> ppExpr i <> char ']'-    CastExpr     ty e -> char '(' <> ppType ty <> char ')' <> ppExpr e-    CompoundExpr ty e -> char '(' <> ppType ty <> char ')' <+> char '{' <> ppExpr e <> char '}'-    PreprocDefined  n -> text "defined(" <> ppLexeme n <> char ')'-    InitialiserList l -> ppInitialiserList l-    PointerAccess e m -> ppExpr e <> text "->" <> ppLexeme m-    MemberAccess  e m -> ppExpr e <> text "." <> ppLexeme m-    CommentExpr   c e -> ppCommentExpr c e-    LicenseDecl l cs  -> ppLicenseDecl l cs+ppVLA :: ADoc -> Lexeme Text -> ADoc -> Doc+ppVLA ty n sz =+    text "VLA("+        <> fst ty+        <> text ", "+        <> ppLexeme n+        <> text ", "+        <> fst sz+        <> char ')' -    x                 -> error $ groom x+ppCompoundStmt :: [ADoc] -> Doc+ppCompoundStmt body =+    nest 2 (+        char '{' <$>+        ppSemiSep body+    ) <$> char '}'  ppTernaryExpr-    :: Show a => Node a (Lexeme Text) -> Node a (Lexeme Text) -> Node a (Lexeme Text) -> Doc+    :: ADoc+    -> ADoc+    -> ADoc+    -> Doc ppTernaryExpr c t e =-    ppExpr c <+> char '?' <+> ppExpr t <+> char ':' <+> ppExpr e+    fst c <+> char '?' <+> fst t <+> char ':' <+> fst e -ppLicenseDecl :: Show a => Lexeme Text -> [Node a (Lexeme Text)] -> Doc+ppLicenseDecl :: Lexeme Text -> [ADoc] -> Doc ppLicenseDecl l cs =-    ppCommentStyle Regular <+> ppLexeme l <$>-    ppLineSep ppCopyrightDecl cs--ppCopyrightDecl :: Show a => Node a (Lexeme Text) -> Doc-ppCopyrightDecl (CopyrightDecl from (Just to) owner) =-    ppLexeme from <> char '-' <> ppLexeme to <+>-    ppCommentWords owner-ppCopyrightDecl (CopyrightDecl from Nothing owner) =-    ppLexeme from <+>-    ppCommentWords owner-ppCopyrightDecl x =-    error $ groom x--ppCommentExpr :: Show a => Node a (Lexeme Text) -> Node a (Lexeme Text) -> Doc-ppCommentExpr (Comment style _ body _) e =-    ppCommentStyle style <+> ppCommentBody body <+> text "*/" <+> ppExpr e-ppCommentExpr c _ = error $ groom c--ppStmt :: Show a => Node a (Lexeme Text) -> Doc-ppStmt = ppDecl--ppDeclList :: Show a => [Node a (Lexeme Text)] -> Doc-ppDeclList = ppLineSep ppDecl--ppDecl :: Show a => Node a (Lexeme Text) -> Doc-ppDecl decl = case decl of-    PreprocElif cond decls (PreprocElse []) ->-        text "#elif" <+> ppExpr cond <$>-        ppDeclList decls <$>-        text "#endif"-    PreprocElif cond decls elseBranch ->-        text "#elif" <+> ppExpr cond <$>-        ppDeclList decls <$>-        ppDeclList [elseBranch] <$>-        text "#endif"-    PreprocIf cond decls (PreprocElse []) ->-        nest (-100) (text "#if") <+> ppExpr cond <$>-        ppDeclList decls <$>-        text "#endif"-    PreprocIf cond decls elseBranch ->-        text "#if" <+> ppExpr cond <$>-        ppDeclList decls <$>-        ppDeclList [elseBranch] <$>-        text "#endif"-    PreprocIfdef name decls (PreprocElse []) ->-        indent (-2) (text "#ifndef" <+> ppLexeme name <$>-        ppDeclList decls) <$>-        text "#endif"-    PreprocIfdef name decls elseBranch ->-        text "#ifdef" <+> ppLexeme name <$>-        ppDeclList decls <$>-        ppDeclList [elseBranch] <$>-        text "#endif"-    PreprocIfndef name decls (PreprocElse []) ->-        text "#ifndef" <+> ppLexeme name <$>-        ppDeclList decls <$>-        text "#endif"-    PreprocIfndef name decls elseBranch ->-        text "#ifndef" <+> ppLexeme name <$>-        ppDeclList decls <$>-        ppDeclList [elseBranch] <$>-        text "#endif"-    PreprocElse decls ->-        text "#else" <$>-        ppDeclList decls--    PreprocScopedDefine def stmts undef ->-        ppDecl def <$> ppStmtList stmts <$> ppDecl undef+    ppCommentStyle Regular <+> text "SPDX-License-Identifier: " <> ppLexeme l <$>+    ppLineSep cs <$>+    text " */" -    PreprocInclude hdr ->-        text "#include" <+> ppLexeme hdr-    PreprocDefine name ->-        text "#define" <+> ppLexeme name-    PreprocDefineConst name value ->-        text "#define" <+> ppLexeme name <+> ppExpr value-    PreprocDefineMacro name params body ->-        text "#define" <+> ppLexeme name <> ppMacroParamList params <+> ppMacroBody body-    PreprocUndef name ->-        text "#undef" <+> ppLexeme name+ppNode :: Node (Lexeme Text) -> ADoc+ppNode = foldFix go+  where+  go :: NodeF (Lexeme Text) ADoc -> ADoc+  go = \case+    StaticAssert cond msg -> semi $+        text "static_assert(" <+> fst cond <> char ',' <+> ppLexeme msg <> char ')' -    StaticAssert cond msg ->-        text "static_assert" <+> ppExpr cond <> char ',' <+> ppLexeme msg <> text ");"+    LicenseDecl l cs -> bare $ ppLicenseDecl l cs+    CopyrightDecl from (Just to) owner -> bare $+        text " * Copyright © " <>+        ppLexeme from <> char '-' <> ppLexeme to <>+        ppCommentBody owner+    CopyrightDecl from Nothing owner -> bare $+        text " * Copyright © " <>+        ppLexeme from <>+        ppCommentBody owner -    Comment style _ cs _ ->+    Comment style _ cs _ -> bare $         ppComment style cs-    CommentBlock cs ->+    CommentBlock cs -> bare $         ppLexeme cs-    Commented c d ->-        ppDecl c <$> ppDecl d+    Commented (c, _) (d, s) -> (, s) $+        c <$> d -    ClassForward name [] ->-        text "class" <+> ppLexeme name <> char ';'-    Class scope name tyvars decls ->-        ppScope scope <>-        nest 2 (-            text "class" <+> ppLexeme name <> ppTypeParams tyvars <+> char '{' <$>-            ppDeclList decls-        ) <$> text "};"+    VarExpr var       -> semi $ ppLexeme var+    LiteralExpr _ l   -> semi $ ppLexeme l+    SizeofExpr arg    -> semi $ text "sizeof(" <> fst arg <> char ')'+    SizeofType arg    -> semi $ text "sizeof(" <> fst arg <> char ')'+    BinaryExpr  l o r -> semi $ fst l <+> ppBinaryOp o <+> fst r+    AssignExpr  l o r -> semi $ fst l <+> ppAssignOp o <+> fst r+    TernaryExpr c t e -> semi $ ppTernaryExpr c t e+    UnaryExpr o e     -> semi $ ppUnaryOp o <> fst e+    ParenExpr e       -> semi $ char '(' <> fst e <> char ')'+    FunctionCall c  a -> semi $ ppFunctionCall c a+    ArrayAccess  e  i -> semi $ fst e <> char '[' <> fst i <> char ']'+    CastExpr     ty e -> semi $ char '(' <> fst ty <> char ')' <> fst e+    CompoundExpr ty e -> semi $ char '(' <> fst ty <> char ')' <+> char '{' <> fst e <> char '}'+    PreprocDefined  n -> bare $ text "defined(" <> ppLexeme n <> char ')'+    InitialiserList l -> semi $ ppInitialiserList l+    PointerAccess e m -> semi $ fst e <> text "->" <> ppLexeme m+    MemberAccess  e m -> semi $ fst e <> text "." <> ppLexeme m+    CommentExpr   c e -> semi $ fst c <+> fst e+    Ellipsis          -> semi $ text "..." -    EnumConsts Nothing enums ->-        nest 2 (-            text "enum" <+> char '{' <$>-            ppEnumeratorList enums-        ) <$> text "};"-    EnumConsts (Just name) enums ->-        nest 2 (-            text "enum" <+> ppLexeme name <+> char '{' <$>-            ppEnumeratorList enums-        ) <$> text "};"-    EnumClass name enums ->-        nest 2 (-            text "enum class" <+> ppLexeme name <+> char '{' <$>-            ppEnumeratorList enums-        ) <$> text "};"-    EnumDecl name enums ty ->-        nest 2 (-            text "typedef enum" <+> ppLexeme name <+> char '{' <$>-            ppEnumeratorList enums-        ) <$> text "} " <> ppLexeme ty <> char ';'+    Declarator dspec Nothing -> dspec+    Declarator dspec (Just initr) -> bare $ fst dspec <+> char '=' <+> fst initr -    Namespace scope name decls ->-        ppNamespace ppDeclList scope name decls+    DeclSpecVar var -> bare $ ppLexeme var+    DeclSpecArray dspec Nothing     -> bare $ fst dspec <> text "[]"+    DeclSpecArray dspec (Just dim)  -> bare $ fst dspec <> char '[' <> fst dim <> char ']' -    ExternC decls ->+    TyPointer     ty -> bare $ fst ty <> char '*'+    TyConst       ty -> bare $ fst ty <+> text "const"+    TyUserDefined l  -> bare $ ppLexeme l+    TyStd         l  -> bare $ ppLexeme l+    TyFunc        l  -> bare $ ppLexeme l+    TyStruct      l  -> bare $ text "struct" <+> ppLexeme l++    ExternC decls -> bare $         text "#ifndef __cplusplus" <$>         text "extern \"C\" {" <$>         text "#endif" <$>-        ppDeclList decls <$>+        ppSemiSep decls <$>         text "#ifndef __cplusplus" <$>         text "}" <$>         text "#endif" -    Struct name members ->-        nest 2 (-            text "struct" <+> ppLexeme name <+> char '{' <$>-            ppMemberDeclList members-        ) <$> text "};"-    Typedef (Union name members) tyname ->-        nest 2 (-            text "typedef union" <+> ppLexeme name <+> char '{' <$>-            ppMemberDeclList members-        ) <$> char '}' <+> ppLexeme tyname <> char ';'-    Typedef (Struct name members) tyname ->-        nest 2 (-            text "typedef struct" <+> ppLexeme name <+> char '{' <$>-            ppMemberDeclList members-        ) <$> char '}' <+> ppLexeme tyname <> char ';'-    Typedef ty name ->-        text "typedef" <+> ppType ty <+> ppLexeme name <> char ';'-    TypedefFunction (FunctionPrototype ty name params) ->-        text "typedef" <+>-        ppFunctionPrototype ty name params <>-        char ';'+    MacroParam l -> bare $ ppLexeme l -    MemberDecl ty dspec Nothing ->-        ppType ty <+> ppDeclSpec dspec <> char ';'-    MemberDecl ty dspec (Just size) ->-        ppType ty <+> ppDeclSpec dspec <+> char ':' <+> ppLexeme size <> char ';'+    MacroBodyFunCall e -> e+    MacroBodyStmt body -> bare $+        text "do" <+> fst body <+> text "while (0)" -    FunctionDecl scope (FunctionPrototype ty name params) err ->-        ppScope scope <>-        ppFunctionPrototype ty name params <>-        ppWithError err-    FunctionDefn scope (FunctionPrototype ty name params) body ->-        ppScope scope <>-        ppFunctionPrototype ty name params <$>-        ppCompoundStmt body+    PreprocScopedDefine def stmts undef -> bare $+        fst def <$> ppSemiSep stmts <$> fst undef -    ConstDecl ty name ->-        text "extern const" <+> ppType ty <+> ppLexeme name <> char ';'-    ConstDefn scope ty name value ->-        ppScope scope <>-        ppType ty <+> ppLexeme name <+> char '=' <+> ppExpr value <> char ';'+    PreprocInclude hdr -> bare $+        text "#include" <+> ppLexeme hdr+    PreprocDefine name -> bare $+        text "#define" <+> ppLexeme name+    PreprocDefineConst name value -> bare $+        text "#define" <+> ppLexeme name <+> fst value+    PreprocDefineMacro name params body -> bare $+        text "#define" <+> ppLexeme name <> ppMacroParamList params <+> fst body+    PreprocUndef name -> bare $+        text "#undef" <+> ppLexeme name -    Event name ty ->+    PreprocIf cond decls elseBranch -> bare $+        text "#if" <+> fst cond <$>+        ppSemiSep decls <>+        fst elseBranch <$>+        text "#endif"+    PreprocIfdef name decls elseBranch -> bare $+        text "#ifdef" <+> ppLexeme name <$>+        ppSemiSep decls <>+        fst elseBranch <$>+        text "#endif"+    PreprocIfndef name decls elseBranch -> bare $+        text "#ifndef" <+> ppLexeme name <$>+        ppSemiSep decls <>+        fst elseBranch <$>+        text "#endif"+    PreprocElse [] -> bare $ empty+    PreprocElse decls -> bare $+        linebreak <>+        text "#else" <$>+        ppSemiSep decls+    PreprocElif cond decls elseBranch -> bare $+        text "#elif" <+> fst cond <$>+        ppSemiSep decls <>+        fst elseBranch <$>+        text "#endif"++    FunctionParam ty dspec -> bare $ fst ty <+> fst dspec+    FunctionPrototype ty name params -> bare $+        ppFunctionPrototype ty name params+    FunctionDecl scope proto -> semi $+        ppScope scope <> fst proto+    FunctionDefn scope proto body -> bare $+        ppScope scope <> fst proto <+> fst body++    MemberDecl ty dspec Nothing -> semi $+        fst ty <+> fst dspec+    MemberDecl ty dspec (Just size) -> semi $+        fst ty <+> fst dspec <+> char ':' <+> ppLexeme size++    Struct name members -> semi $         nest 2 (-            text "event" <+> ppLexeme name <+> char '{' <$>-            ppEventType ty+            text "struct" <+> ppLexeme name <+> char '{' <$>+            ppSemiSep members         ) <$> char '}'--    Property ty dspec accessors ->+    Union name members -> semi $         nest 2 (-            ppType ty <+> ppDeclSpec dspec <+> char '{' <$>-            ppAccessorList accessors+            text "union" <+> ppLexeme name <+> char '{' <$>+            ppSemiSep members         ) <$> char '}'+    Typedef ty tyname -> semi $+        text "typedef" <+> fst ty <+> ppLexeme tyname+    TypedefFunction proto -> semi $+        text "typedef" <+> fst proto -    ErrorDecl name errs ->+    ConstDecl ty name -> semi $+        text "extern const" <+> fst ty <+> ppLexeme name+    ConstDefn scope ty name value -> semi $+        ppScope scope <> text "const" <+>+        fst ty <+> ppLexeme name <+> char '=' <+> fst value++    Enumerator name  Nothing -> bare $ ppLexeme name <> char ','+    Enumerator name (Just value) -> bare $+        ppLexeme name <+> char '=' <+> fst value <> char ','++    EnumConsts Nothing enums -> semi $         nest 2 (-            text "error for" <+> ppLexeme name <+> char '{' <$>-            ppEnumeratorList errs+            text "enum" <+> char '{' <$>+            ppLineSep enums         ) <$> char '}'+    EnumConsts (Just name) enums -> semi $+        nest 2 (+            text "enum" <+> ppLexeme name <+> char '{' <$>+            ppLineSep enums+        ) <$> char '}'+    EnumDecl name enums ty -> semi $+        nest 2 (+            text "typedef enum" <+> ppLexeme name <+> char '{' <$>+            ppLineSep enums+        ) <$> text "} " <> ppLexeme ty      -- Statements-    Continue              -> text "continue;"-    Break                 -> text "break;"-    Return Nothing        -> text "return;"-    Return (Just e)       -> text "return" <+> ppExpr e <> char ';'-    VarDecl ty declr      -> ppType ty <+> ppDeclarator declr <> char ';'-    IfStmt cond t e       -> ppIfStmt cond t e-    ForStmt i c n body    -> ppForStmt i c n body-    Default s             -> text "default:" <+> ppStmt s-    Label l s             -> ppLexeme l <> char ':' <$> ppStmt s-    Goto l                -> text "goto " <> ppLexeme l <> char ';'-    Case        e    s    -> text "case " <> ppExpr e <> char ':' <+> ppStmt s-    WhileStmt   c    body -> ppWhileStmt c body-    DoWhileStmt body c    -> ppDoWhileStmt body c-    SwitchStmt  c    body -> ppSwitchStmt c body-    CompoundStmt body     -> char '{' <$> ppStmtList body <$> char '}'-    VLA ty n sz           -> ppVLA ty n sz--    x                     -> ppExpr x <> char ';'+    VarDecl ty declr   -> semi $ fst ty <+> fst declr+    Return Nothing     -> semi $ text "return"+    Return (Just e)    -> semi $ text "return" <+> fst e+    Continue           -> semi $ text "continue"+    Break              -> semi $ text "break"+    IfStmt cond t e    -> bare $ ppIfStmt cond t e+    ForStmt i c n body -> bare $ ppForStmt i c n body+    Default s          -> cp s $ text "default:" <+> fst s+    Label l s          -> bare $ ppLexeme l <> char ':' <$> fst s+    Goto l             -> semi $ text "goto " <> ppLexeme l+    Case e s           -> cp s $ text "case " <> fst e <> char ':' <+> fst s+    WhileStmt c body   -> bare $ ppWhileStmt c body+    DoWhileStmt body c -> semi $ ppDoWhileStmt body c+    SwitchStmt c body  -> bare $ ppSwitchStmt c body+    CompoundStmt body  -> bare $ ppCompoundStmt body+    VLA ty n sz        -> semi $ ppVLA ty n sz  -ppVLA :: Show a => Node a (Lexeme Text) -> Lexeme Text -> Node a (Lexeme Text) -> Doc-ppVLA ty n sz =-    text "VLA("-        <> ppType ty-        <> text ", "-        <> ppLexeme n-        <> text ", "-        <> ppExpr sz-        <> text ");"--ppTranslationUnit :: Show a => [Node a (Lexeme Text)] -> Doc-ppTranslationUnit decls = ppDeclList decls <> linebreak+ppTranslationUnit :: [Node (Lexeme Text)] -> Doc+ppTranslationUnit decls = ppSemiSep (map ppNode decls) <> linebreak
src/Language/Cimple/Program.hs view
@@ -10,7 +10,7 @@ import           Data.Map.Strict                   (Map) import qualified Data.Map.Strict                   as Map import           Data.Text                         (Text)-import           Language.Cimple.AST               (Node (..))+import           Language.Cimple.AST               (Node) import           Language.Cimple.Graph             (Graph) import qualified Language.Cimple.Graph             as Graph import           Language.Cimple.Lexer             (Lexeme (..))@@ -20,7 +20,7 @@   data Program text = Program-  { progAsts     :: Map FilePath [Node () (Lexeme text)]+  { progAsts     :: Map FilePath [Node (Lexeme text)]   , progIncludes :: Graph () FilePath   } 
src/Language/Cimple/SemCheck/Includes.hs view
@@ -6,9 +6,10 @@  import           Control.Monad.State.Lazy        (State) import qualified Control.Monad.State.Lazy        as State+import           Data.Fix                        (Fix (..)) import           Data.Text                       (Text) import qualified Data.Text                       as Text-import           Language.Cimple.AST             (Node (..))+import           Language.Cimple.AST             (NodeF (..)) import           Language.Cimple.Lexer           (Lexeme (..)) import           Language.Cimple.Tokens          (LexemeClass (..)) import           Language.Cimple.TranslationUnit (TranslationUnit)@@ -36,14 +37,14 @@     go d f         = joinPath (d ++ f)  -normaliseIncludes' :: FilePath -> IdentityActions (State [FilePath]) () Text+normaliseIncludes' :: FilePath -> IdentityActions (State [FilePath]) Text normaliseIncludes' dir = identityActions     { doNode = \_ node act ->         case node of-            PreprocInclude (L spos LitString include) -> do+            Fix (PreprocInclude (L spos LitString include)) -> do                 let includePath = relativeTo dir $ tread include                 State.modify (includePath :)-                return $ PreprocInclude (L spos LitString (tshow includePath))+                return $ Fix $ PreprocInclude (L spos LitString (tshow includePath))              _ -> act     }
src/Language/Cimple/Tokens.hs view
@@ -12,38 +12,30 @@     | IdFuncType     | IdStdType     | IdSueType-    | IdTyVar     | IdVar-    | KwBitmask     | KwBreak     | KwCase-    | KwClass     | KwConst     | KwContinue     | KwDefault     | KwDo     | KwElse     | KwEnum-    | KwError-    | KwEvent     | KwExtern     | KwFor     | KwGoto     | KwIf-    | KwNamespace     | KwReturn     | KwSizeof     | KwStatic     | KwStaticAssert     | KwStruct     | KwSwitch-    | KwThis     | KwTypedef     | KwUnion     | KwVla     | KwVoid     | KwWhile-    | KwWith     | LitFalse     | LitTrue     | LitChar
src/Language/Cimple/TranslationUnit.hs view
@@ -6,4 +6,4 @@ import           Language.Cimple.AST   (Node) import           Language.Cimple.Lexer (Lexeme) -type TranslationUnit text = (FilePath, [Node () (Lexeme text)])+type TranslationUnit text = (FilePath, [Node (Lexeme text)])
src/Language/Cimple/TraverseAst.hs view
@@ -6,305 +6,278 @@ {-# LANGUAGE RecordWildCards       #-} {-# LANGUAGE ScopedTypeVariables   #-} {-# LANGUAGE StrictData            #-}+{-# LANGUAGE TypeFamilies          #-} module Language.Cimple.TraverseAst-    ( mapAst, traverseAst+    ( traverseAst      , doFiles, doFile     , doNodes, doNode     , doLexemes, doLexeme     , doText-    , doAttr      , astActions-    , AttrActions, attrActions     , TextActions, textActions     , IdentityActions, identityActions     ) where -import           Language.Cimple.AST   (Node (..))+import           Data.Fix              (Fix (..))+import           Language.Cimple.AST   (Node, NodeF (..)) import           Language.Cimple.Lexer (Lexeme (..)) -class TraverseAst iattr oattr itext otext a b where-    mapAst :: Applicative f => AstActions f iattr oattr itext otext -> a -> f b+class TraverseAst itext otext a where+    type Mapped itext otext a+    mapFileAst+        :: Applicative f+        => AstActions f itext otext+        -> FilePath+        -> a+        -> f (Mapped itext otext a)  traverseAst-    :: (TraverseAst iattr oattr itext otext a a, Applicative f)-    => AstActions f iattr oattr itext otext -> a -> f a-traverseAst = mapAst+    :: (TraverseAst itext otext    a, Applicative f)+    => AstActions f itext otext -> a+    -> f    (Mapped itext otext    a)+traverseAst = flip mapFileAst "<stdin>" -data AstActions f iattr oattr itext otext = AstActions-    { currentFile :: FilePath-    , doFiles     :: [(FilePath, [Node iattr (Lexeme itext)])] -> f [(FilePath, [Node oattr (Lexeme otext)])] -> f [(FilePath, [Node oattr (Lexeme otext)])]-    , doFile      ::  (FilePath, [Node iattr (Lexeme itext)])  -> f  (FilePath, [Node oattr (Lexeme otext)])  -> f  (FilePath, [Node oattr (Lexeme otext)])-    , doNodes     :: FilePath -> [Node iattr (Lexeme itext)]   -> f             [Node oattr (Lexeme otext)]   -> f             [Node oattr (Lexeme otext)]-    , doNode      :: FilePath ->  Node iattr (Lexeme itext)    -> f             (Node oattr (Lexeme otext))   -> f             (Node oattr (Lexeme otext))-    , doLexemes   :: FilePath ->             [Lexeme itext]    -> f                         [Lexeme otext]    -> f                         [Lexeme otext]-    , doLexeme    :: FilePath ->              Lexeme itext     -> f                         (Lexeme otext)    -> f                         (Lexeme otext)-    , doText      :: FilePath ->                     itext                                                    -> f                                 otext-    , doAttr      :: FilePath ->       iattr                                                                  -> f                   oattr+data AstActions f itext otext = AstActions+    { doFiles     :: [(FilePath, [Node (Lexeme itext)])] -> f [(FilePath, [Node (Lexeme otext)])] -> f [(FilePath, [Node (Lexeme otext)])]+    , doFile      ::  (FilePath, [Node (Lexeme itext)])  -> f  (FilePath, [Node (Lexeme otext)])  -> f  (FilePath, [Node (Lexeme otext)])+    , doNodes     :: FilePath -> [Node (Lexeme itext)]   -> f             [Node (Lexeme otext)]   -> f             [Node (Lexeme otext)]+    , doNode      :: FilePath ->  Node (Lexeme itext)    -> f             (Node (Lexeme otext))   -> f             (Node (Lexeme otext))+    , doLexemes   :: FilePath ->       [Lexeme itext]    -> f                   [Lexeme otext]    -> f                   [Lexeme otext]+    , doLexeme    :: FilePath ->        Lexeme itext     -> f                   (Lexeme otext)    -> f                   (Lexeme otext)+    , doText      :: FilePath ->               itext                                              -> f                           otext     } -instance TraverseAst iattr oattr itext otext        a         b-      => TraverseAst iattr oattr itext otext (Maybe a) (Maybe b) where-    mapAst _       Nothing  = pure Nothing-    mapAst actions (Just x) = Just <$> mapAst actions x+instance TraverseAst itext otext        a+      => TraverseAst itext otext (Maybe a) where+    type        Mapped itext otext (Maybe a)+       = Maybe (Mapped itext otext        a)+    mapFileAst _       _           Nothing  = pure Nothing+    mapFileAst actions currentFile (Just x) = Just <$> mapFileAst actions currentFile x  astActions     :: Applicative f-    => (iattr -> f oattr)-    -> (itext -> f otext)-    -> AstActions f iattr oattr itext otext-astActions fa ft = AstActions-    { currentFile = "<stdin>"-    , doFiles     = const id+    => (itext -> f otext)+    -> AstActions f itext otext+astActions ft = AstActions+    { doFiles     = const id     , doFile      = const id     , doNodes     = const $ const id     , doNode      = const $ const id     , doLexeme    = const $ const id     , doLexemes   = const $ const id     , doText      = const ft-    , doAttr      = const fa     } -type AttrActions f iattr oattr text = AstActions f iattr oattr text text-attrActions :: Applicative f => (iattr -> f oattr) -> AttrActions f iattr oattr text-attrActions = flip astActions pure--type TextActions f attr itext otext = AstActions f attr attr itext otext-textActions :: Applicative f => (itext -> f otext) -> TextActions f attr itext otext-textActions = astActions pure+type TextActions f itext otext = AstActions f itext otext+textActions :: Applicative f => (itext -> f otext) -> TextActions f itext otext+textActions = astActions -type IdentityActions f attr text = AstActions f attr attr text text-identityActions :: Applicative f => AstActions f attr attr text text-identityActions = astActions pure pure+type IdentityActions f text = AstActions f text text+identityActions :: Applicative f => AstActions f text text+identityActions = astActions pure  -instance TraverseAst iattr oattr itext otext itext otext where-    mapAst AstActions{..} = doText currentFile--instance TraverseAst iattr oattr itext otext iattr oattr where-    mapAst AstActions{..} = doAttr currentFile--instance TraverseAst iattr oattr itext otext (Lexeme itext)-                                             (Lexeme otext) where-    mapAst :: forall f . Applicative f-           => AstActions f iattr oattr itext otext -> Lexeme itext -> f (Lexeme otext)-    mapAst actions@AstActions{..} = doLexeme currentFile <*>-        \(L p c s) -> L p c <$> recurse s-      where-        recurse :: TraverseAst iattr oattr itext otext a b => a -> f b-        recurse = mapAst actions+instance TraverseAst itext otext (Lexeme itext) where+    type Mapped itext otext (Lexeme itext)+                          =  Lexeme otext+    mapFileAst :: forall f . Applicative f+               => AstActions f itext otext -> FilePath -> Lexeme itext -> f (Lexeme otext)+    mapFileAst AstActions{..} currentFile = doLexeme currentFile <*>+        \(L p c s) -> L p c <$> doText currentFile s -instance TraverseAst iattr oattr itext otext [Lexeme itext]-                                             [Lexeme otext] where-    mapAst actions@AstActions{..} = doLexemes currentFile <*>-        traverse (mapAst actions)+instance TraverseAst itext otext [Lexeme itext] where+    type Mapped itext otext [Lexeme itext]+                          = [Lexeme otext]+    mapFileAst actions@AstActions{..} currentFile = doLexemes currentFile <*>+        traverse (mapFileAst actions currentFile) -instance TraverseAst iattr oattr itext otext (Node iattr (Lexeme itext))-                                             (Node oattr (Lexeme otext)) where-    mapAst :: forall f . Applicative f-           => AstActions f iattr oattr itext otext -> Node iattr (Lexeme itext) -> f (Node oattr (Lexeme otext))-    mapAst actions@AstActions{..} = doNode currentFile <*> \case-        Attr attr node ->-            Attr <$> recurse attr <*> recurse node+instance TraverseAst itext otext (Node (Lexeme itext)) where+    type Mapped itext otext (Node (Lexeme itext))+                          =  Node (Lexeme otext)+    mapFileAst+        :: forall f . Applicative f+        => AstActions f itext otext+        -> FilePath+        ->    Node (Lexeme itext)+        -> f (Node (Lexeme otext))+    mapFileAst actions@AstActions{..} currentFile = doNode currentFile <*> \node -> case unFix node of         PreprocInclude path ->-            PreprocInclude <$> recurse path+            Fix <$> (PreprocInclude <$> recurse path)         PreprocDefine name ->-            PreprocDefine <$> recurse name+            Fix <$> (PreprocDefine <$> recurse name)         PreprocDefineConst name value ->-            PreprocDefineConst <$> recurse name <*> recurse value+            Fix <$> (PreprocDefineConst <$> recurse name <*> recurse value)         PreprocDefineMacro name params body ->-            PreprocDefineMacro <$> recurse name <*> recurse params <*> recurse body+            Fix <$> (PreprocDefineMacro <$> recurse name <*> recurse params <*> recurse body)         PreprocIf cond thenDecls elseBranch ->-            PreprocIf <$> recurse cond <*> recurse thenDecls <*> recurse elseBranch+            Fix <$> (PreprocIf <$> recurse cond <*> recurse thenDecls <*> recurse elseBranch)         PreprocIfdef name thenDecls elseBranch ->-            PreprocIfdef <$> recurse name <*> recurse thenDecls <*> recurse elseBranch+            Fix <$> (PreprocIfdef <$> recurse name <*> recurse thenDecls <*> recurse elseBranch)         PreprocIfndef name thenDecls elseBranch ->-            PreprocIfndef <$> recurse name <*> recurse thenDecls <*> recurse elseBranch+            Fix <$> (PreprocIfndef <$> recurse name <*> recurse thenDecls <*> recurse elseBranch)         PreprocElse decls ->-            PreprocElse <$> recurse decls+            Fix <$> (PreprocElse <$> recurse decls)         PreprocElif cond decls elseBranch ->-            PreprocElif <$> recurse cond <*> recurse decls <*> recurse elseBranch+            Fix <$> (PreprocElif <$> recurse cond <*> recurse decls <*> recurse elseBranch)         PreprocUndef name ->-            PreprocUndef <$> recurse name+            Fix <$> (PreprocUndef <$> recurse name)         PreprocDefined name ->-            PreprocDefined <$> recurse name+            Fix <$> (PreprocDefined <$> recurse name)         PreprocScopedDefine define stmts undef ->-            PreprocScopedDefine <$> recurse define <*> recurse stmts <*> recurse undef+            Fix <$> (PreprocScopedDefine <$> recurse define <*> recurse stmts <*> recurse undef)         MacroBodyStmt stmts ->-            MacroBodyStmt <$> recurse stmts+            Fix <$> (MacroBodyStmt <$> recurse stmts)         MacroBodyFunCall expr ->-            MacroBodyFunCall <$> recurse expr+            Fix <$> (MacroBodyFunCall <$> recurse expr)         MacroParam name ->-            MacroParam <$> recurse name+            Fix <$> (MacroParam <$> recurse name)         StaticAssert cond msg ->-            StaticAssert <$> recurse cond <*> recurse msg+            Fix <$> (StaticAssert <$> recurse cond <*> recurse msg)         LicenseDecl license copyrights ->-            LicenseDecl <$> recurse license <*> recurse copyrights+            Fix <$> (LicenseDecl <$> recurse license <*> recurse copyrights)         CopyrightDecl from to owner ->-            CopyrightDecl <$> recurse from <*> recurse to <*> recurse owner+            Fix <$> (CopyrightDecl <$> recurse from <*> recurse to <*> recurse owner)         Comment doc start contents end ->-            Comment doc <$> recurse start <*> recurse contents <*> recurse end+            Fix <$> (Comment doc <$> recurse start <*> recurse contents <*> recurse end)         CommentBlock comment ->-            CommentBlock <$> recurse comment-        CommentWord word ->-            CommentWord <$> recurse word-        Commented comment node ->-            Commented <$> recurse comment <*> recurse node+            Fix <$> (CommentBlock <$> recurse comment)+        Commented comment subject ->+            Fix <$> (Commented <$> recurse comment <*> recurse subject)         ExternC decls ->-            ExternC <$> recurse decls+            Fix <$> (ExternC <$> recurse decls)         CompoundStmt stmts ->-            CompoundStmt <$> recurse stmts+            Fix <$> (CompoundStmt <$> recurse stmts)         Break ->-            pure Break+            Fix <$> (pure Break)         Goto label ->-            Goto <$> recurse label+            Fix <$> (Goto <$> recurse label)         Continue ->-            pure Continue+            Fix <$> (pure Continue)         Return value ->-            Return <$> recurse value+            Fix <$> (Return <$> recurse value)         SwitchStmt value cases ->-            SwitchStmt <$> recurse value <*> recurse cases+            Fix <$> (SwitchStmt <$> recurse value <*> recurse cases)         IfStmt cond thenStmts elseStmt ->-            IfStmt <$> recurse cond <*> recurse thenStmts <*> recurse elseStmt+            Fix <$> (IfStmt <$> recurse cond <*> recurse thenStmts <*> recurse elseStmt)         ForStmt initStmt cond next stmts ->-            ForStmt <$> recurse initStmt <*> recurse cond <*> recurse next <*> recurse stmts+            Fix <$> (ForStmt <$> recurse initStmt <*> recurse cond <*> recurse next <*> recurse stmts)         WhileStmt cond stmts ->-            WhileStmt <$> recurse cond <*> recurse stmts+            Fix <$> (WhileStmt <$> recurse cond <*> recurse stmts)         DoWhileStmt stmts cond ->-            DoWhileStmt <$> recurse stmts <*> recurse cond+            Fix <$> (DoWhileStmt <$> recurse stmts <*> recurse cond)         Case value stmt ->-            Case <$> recurse value <*> recurse stmt+            Fix <$> (Case <$> recurse value <*> recurse stmt)         Default stmt ->-            Default <$> recurse stmt+            Fix <$> (Default <$> recurse stmt)         Label label stmt ->-            Label <$> recurse label <*> recurse stmt+            Fix <$> (Label <$> recurse label <*> recurse stmt)         VLA ty name size ->-            VLA <$> recurse ty <*> recurse name <*> recurse size+            Fix <$> (VLA <$> recurse ty <*> recurse name <*> recurse size)         VarDecl ty decl ->-            VarDecl <$> recurse ty <*> recurse decl+            Fix <$> (VarDecl <$> recurse ty <*> recurse decl)         Declarator spec value ->-            Declarator <$> recurse spec <*> recurse value+            Fix <$> (Declarator <$> recurse spec <*> recurse value)         DeclSpecVar name ->-            DeclSpecVar <$> recurse name+            Fix <$> (DeclSpecVar <$> recurse name)         DeclSpecArray spec size ->-            DeclSpecArray <$> recurse spec <*> recurse size+            Fix <$> (DeclSpecArray <$> recurse spec <*> recurse size)         InitialiserList values ->-            InitialiserList <$> recurse values+            Fix <$> (InitialiserList <$> recurse values)         UnaryExpr op expr ->-            UnaryExpr op <$> recurse expr+            Fix <$> (UnaryExpr op <$> recurse expr)         BinaryExpr lhs op rhs ->-            BinaryExpr <$> recurse lhs <*> pure op <*> recurse rhs+            Fix <$> (BinaryExpr <$> recurse lhs <*> pure op <*> recurse rhs)         TernaryExpr cond thenExpr elseExpr ->-            TernaryExpr <$> recurse cond <*> recurse thenExpr <*> recurse elseExpr+            Fix <$> (TernaryExpr <$> recurse cond <*> recurse thenExpr <*> recurse elseExpr)         AssignExpr lhs op rhs ->-            AssignExpr <$> recurse lhs <*> pure op <*> recurse rhs+            Fix <$> (AssignExpr <$> recurse lhs <*> pure op <*> recurse rhs)         ParenExpr expr ->-            ParenExpr <$> recurse expr+            Fix <$> (ParenExpr <$> recurse expr)         CastExpr ty expr ->-            CastExpr <$> recurse ty <*> recurse expr+            Fix <$> (CastExpr <$> recurse ty <*> recurse expr)         CompoundExpr ty expr ->-            CompoundExpr <$> recurse ty <*> recurse expr+            Fix <$> (CompoundExpr <$> recurse ty <*> recurse expr)         SizeofExpr expr ->-            SizeofExpr <$> recurse expr+            Fix <$> (SizeofExpr <$> recurse expr)         SizeofType ty ->-            SizeofType <$> recurse ty+            Fix <$> (SizeofType <$> recurse ty)         LiteralExpr ty value ->-            LiteralExpr ty <$> recurse value+            Fix <$> (LiteralExpr ty <$> recurse value)         VarExpr name ->-            VarExpr <$> recurse name+            Fix <$> (VarExpr <$> recurse name)         MemberAccess name field ->-            MemberAccess <$> recurse name <*> recurse field+            Fix <$> (MemberAccess <$> recurse name <*> recurse field)         PointerAccess name field ->-            PointerAccess <$> recurse name <*> recurse field+            Fix <$> (PointerAccess <$> recurse name <*> recurse field)         ArrayAccess arr idx ->-            ArrayAccess <$> recurse arr <*> recurse idx+            Fix <$> (ArrayAccess <$> recurse arr <*> recurse idx)         FunctionCall callee args ->-            FunctionCall <$> recurse callee <*> recurse args+            Fix <$> (FunctionCall <$> recurse callee <*> recurse args)         CommentExpr comment expr ->-            CommentExpr <$> recurse comment <*> recurse expr-        EnumClass name members ->-            EnumClass <$> recurse name <*> recurse members+            Fix <$> (CommentExpr <$> recurse comment <*> recurse expr)         EnumConsts name members ->-            EnumConsts <$> recurse name <*> recurse members+            Fix <$> (EnumConsts <$> recurse name <*> recurse members)         EnumDecl name members tyName ->-            EnumDecl <$> recurse name <*> recurse members <*> recurse tyName+            Fix <$> (EnumDecl <$> recurse name <*> recurse members <*> recurse tyName)         Enumerator name value ->-            Enumerator <$> recurse name <*> recurse value+            Fix <$> (Enumerator <$> recurse name <*> recurse value)         Typedef ty name ->-            Typedef <$> recurse ty <*> recurse name+            Fix <$> (Typedef <$> recurse ty <*> recurse name)         TypedefFunction ty ->-            TypedefFunction <$> recurse ty-        Namespace scope name members ->-            Namespace scope <$> recurse name <*> recurse members-        Class scope name tyvars members ->-            Class scope <$> recurse name <*> recurse tyvars <*> recurse members-        ClassForward name tyvars ->-            ClassForward <$> recurse name <*> recurse tyvars+            Fix <$> (TypedefFunction <$> recurse ty)         Struct name members ->-            Struct <$> recurse name <*> recurse members+            Fix <$> (Struct <$> recurse name <*> recurse members)         Union name members ->-            Union <$> recurse name <*> recurse members+            Fix <$> (Union <$> recurse name <*> recurse members)         MemberDecl ty decl width ->-            MemberDecl <$> recurse ty <*> recurse decl <*> recurse width+            Fix <$> (MemberDecl <$> recurse ty <*> recurse decl <*> recurse width)         TyConst ty ->-            TyConst <$> recurse ty+            Fix <$> (TyConst <$> recurse ty)         TyPointer ty ->-            TyPointer <$> recurse ty+            Fix <$> (TyPointer <$> recurse ty)         TyStruct name ->-            TyStruct <$> recurse name+            Fix <$> (TyStruct <$> recurse name)         TyFunc name ->-            TyFunc <$> recurse name-        TyVar name ->-            TyVar <$> recurse name+            Fix <$> (TyFunc <$> recurse name)         TyStd name ->-            TyStd <$> recurse name+            Fix <$> (TyStd <$> recurse name)         TyUserDefined name ->-            TyUserDefined <$> recurse name-        FunctionDecl scope proto errors ->-            FunctionDecl scope <$> recurse proto <*> recurse errors+            Fix <$> (TyUserDefined <$> recurse name)+        FunctionDecl scope proto ->+            Fix <$> (FunctionDecl scope <$> recurse proto)         FunctionDefn scope proto body ->-            FunctionDefn scope <$> recurse proto <*> recurse body+            Fix <$> (FunctionDefn scope <$> recurse proto <*> recurse body)         FunctionPrototype ty name params ->-            FunctionPrototype <$> recurse ty <*> recurse name <*> recurse params+            Fix <$> (FunctionPrototype <$> recurse ty <*> recurse name <*> recurse params)         FunctionParam ty decl ->-            FunctionParam <$> recurse ty <*> recurse decl-        Event name params ->-            Event <$> recurse name <*> recurse params-        EventParams params ->-            EventParams <$> recurse params-        Property ty decl accessors ->-            Property <$> recurse ty <*> recurse decl <*> recurse accessors-        Accessor name params errors ->-            Accessor <$> recurse name <*> recurse params <*> recurse errors-        ErrorDecl name errors ->-            ErrorDecl <$> recurse name <*> recurse errors-        ErrorList errors ->-            ErrorList <$> recurse errors-        ErrorFor name ->-            ErrorFor <$> recurse name+            Fix <$> (FunctionParam <$> recurse ty <*> recurse decl)         Ellipsis ->-            pure Ellipsis+            Fix <$> (pure Ellipsis)         ConstDecl ty name ->-            ConstDecl <$> recurse ty <*> recurse name+            Fix <$> (ConstDecl <$> recurse ty <*> recurse name)         ConstDefn scope ty name value ->-            ConstDefn scope <$> recurse ty <*> recurse name <*> recurse value+            Fix <$> (ConstDefn scope <$> recurse ty <*> recurse name <*> recurse value)        where-        recurse :: TraverseAst iattr oattr itext otext a b => a -> f b-        recurse = mapAst actions+        recurse :: TraverseAst itext otext a => a -> f (Mapped itext otext a)+        recurse = mapFileAst actions currentFile -instance TraverseAst iattr oattr itext otext [Node iattr (Lexeme itext)]-                                             [Node oattr (Lexeme otext)] where-    mapAst actions@AstActions{..} = doNodes currentFile <*>-        traverse (mapAst actions)+instance TraverseAst itext otext [Node (Lexeme itext)] where+    type Mapped itext otext [Node (Lexeme itext)]+                          = [Node (Lexeme otext)]+    mapFileAst actions@AstActions{..} currentFile = doNodes currentFile <*>+        traverse (mapFileAst actions currentFile) -instance TraverseAst iattr oattr itext otext (FilePath, [Node iattr (Lexeme itext)])-                                             (FilePath, [Node oattr (Lexeme otext)]) where-    mapAst actions@AstActions{doFile} tu@(currentFile, _) = doFile <*>-        traverse (mapAst actions{currentFile}) $ tu+instance TraverseAst itext otext (FilePath, [Node (Lexeme itext)]) where+    type Mapped itext otext (FilePath, [Node (Lexeme itext)])+                          = (FilePath, [Node (Lexeme otext)])+    mapFileAst actions@AstActions{..} _ tu@(currentFile, _) = doFile <*>+        traverse (mapFileAst actions currentFile) $ tu -instance TraverseAst iattr oattr itext otext [(FilePath, [Node iattr (Lexeme itext)])]-                                             [(FilePath, [Node oattr (Lexeme otext)])] where-    mapAst actions@AstActions{..} = doFiles <*>-        traverse (mapAst actions)+instance TraverseAst itext otext [(FilePath, [Node (Lexeme itext)])] where+    type Mapped itext otext [(FilePath, [Node (Lexeme itext)])]+                          = [(FilePath, [Node (Lexeme otext)])]+    mapFileAst actions@AstActions{..} currentFile = doFiles <*>+        traverse (mapFileAst actions currentFile)
src/Language/Cimple/TreeParser.y view
@@ -6,8 +6,9 @@     , toEither     ) where +import           Data.Fix              (Fix (..)) import           Data.Text             (Text)-import           Language.Cimple.AST   (CommentStyle (..), Node (..))+import           Language.Cimple.AST   (CommentStyle (..), Node, NodeF (..)) import           Language.Cimple.Lexer (Lexeme) } @@ -20,116 +21,103 @@ %monad {TreeParser} %tokentype {TextNode} %token-    ifndefDefine	{ PreprocIfndef _ body (PreprocElse []) | isDefine body }-    ifdefDefine		{ PreprocIfdef _ body (PreprocElse []) | isDefine body }-    ifDefine		{ PreprocIf _ body (PreprocElse []) | isDefine body }+    ifndefDefine	{ Fix (PreprocIfndef _ body (Fix (PreprocElse []))) | isDefine body }+    ifdefDefine		{ Fix (PreprocIfdef _ body (Fix (PreprocElse []))) | isDefine body }+    ifDefine		{ Fix (PreprocIf _ body (Fix (PreprocElse []))) | isDefine body } -    ifndefInclude	{ PreprocIfndef{} | isPreproc tk && hasInclude tk }-    ifdefInclude	{ PreprocIfdef{} | isPreproc tk && hasInclude tk }-    ifInclude		{ PreprocIf{} | isPreproc tk && hasInclude tk }+    ifndefInclude	{ Fix (PreprocIfndef{}) | isPreproc tk && hasInclude tk }+    ifdefInclude	{ Fix (PreprocIfdef{}) | isPreproc tk && hasInclude tk }+    ifInclude		{ Fix (PreprocIf{}) | isPreproc tk && hasInclude tk } -    docComment		{ Comment Doxygen _ _ _ }+    docComment		{ Fix (Comment Doxygen _ _ _) }      -- Preprocessor-    preprocInclude	{ PreprocInclude{} }-    preprocDefine	{ PreprocDefine{} }-    preprocDefineConst	{ PreprocDefineConst{} }-    preprocDefineMacro	{ PreprocDefineMacro{} }-    preprocIf		{ PreprocIf{} }-    preprocIfdef	{ PreprocIfdef{} }-    preprocIfndef	{ PreprocIfndef{} }-    preprocElse		{ PreprocElse{} }-    preprocElif		{ PreprocElif{} }-    preprocUndef	{ PreprocUndef{} }-    preprocDefined	{ PreprocDefined{} }-    preprocScopedDefine	{ PreprocScopedDefine{} }-    macroBodyStmt	{ MacroBodyStmt{} }-    macroBodyFunCall	{ MacroBodyFunCall{} }-    macroParam		{ MacroParam{} }-    staticAssert	{ StaticAssert{} }+    preprocInclude	{ Fix (PreprocInclude{}) }+    preprocDefine	{ Fix (PreprocDefine{}) }+    preprocDefineConst	{ Fix (PreprocDefineConst{}) }+    preprocDefineMacro	{ Fix (PreprocDefineMacro{}) }+    preprocIf		{ Fix (PreprocIf{}) }+    preprocIfdef	{ Fix (PreprocIfdef{}) }+    preprocIfndef	{ Fix (PreprocIfndef{}) }+    preprocElse		{ Fix (PreprocElse{}) }+    preprocElif		{ Fix (PreprocElif{}) }+    preprocUndef	{ Fix (PreprocUndef{}) }+    preprocDefined	{ Fix (PreprocDefined{}) }+    preprocScopedDefine	{ Fix (PreprocScopedDefine{}) }+    macroBodyStmt	{ Fix (MacroBodyStmt{}) }+    macroBodyFunCall	{ Fix (MacroBodyFunCall{}) }+    macroParam		{ Fix (MacroParam{}) }+    staticAssert	{ Fix (StaticAssert{}) }     -- Comments-    licenseDecl		{ LicenseDecl{} }-    copyrightDecl	{ CopyrightDecl{} }-    comment		{ Comment{} }-    commentBlock	{ CommentBlock{} }-    commentWord		{ CommentWord{} }-    commented		{ Commented{} }+    licenseDecl		{ Fix (LicenseDecl{}) }+    copyrightDecl	{ Fix (CopyrightDecl{}) }+    comment		{ Fix (Comment{}) }+    commentBlock	{ Fix (CommentBlock{}) }+    commented		{ Fix (Commented{}) }     -- Namespace-like blocks-    externC		{ ExternC{} }-    class		{ Class{} }-    namespace		{ Namespace{} }+    externC		{ Fix (ExternC{}) }     -- Statements-    compoundStmt	{ CompoundStmt{} }-    break		{ Break }-    goto		{ Goto{} }-    continue		{ Continue }-    return		{ Return{} }-    switchStmt		{ SwitchStmt{} }-    ifStmt		{ IfStmt{} }-    forStmt		{ ForStmt{} }-    whileStmt		{ WhileStmt{} }-    doWhileStmt		{ DoWhileStmt{} }-    case		{ Case{} }-    default		{ Default{} }-    label		{ Label{} }+    compoundStmt	{ Fix (CompoundStmt{}) }+    break		{ Fix (Break) }+    goto		{ Fix (Goto{}) }+    continue		{ Fix (Continue) }+    return		{ Fix (Return{}) }+    switchStmt		{ Fix (SwitchStmt{}) }+    ifStmt		{ Fix (IfStmt{}) }+    forStmt		{ Fix (ForStmt{}) }+    whileStmt		{ Fix (WhileStmt{}) }+    doWhileStmt		{ Fix (DoWhileStmt{}) }+    case		{ Fix (Case{}) }+    default		{ Fix (Default{}) }+    label		{ Fix (Label{}) }     -- Variable declarations-    vLA			{ VLA{} }-    varDecl		{ VarDecl{} }-    declarator		{ Declarator{} }-    declSpecVar		{ DeclSpecVar{} }-    declSpecArray	{ DeclSpecArray{} }+    vLA			{ Fix (VLA{}) }+    varDecl		{ Fix (VarDecl{}) }+    declarator		{ Fix (Declarator{}) }+    declSpecVar		{ Fix (DeclSpecVar{}) }+    declSpecArray	{ Fix (DeclSpecArray{}) }     -- Expressions-    initialiserList	{ InitialiserList{} }-    unaryExpr		{ UnaryExpr{} }-    binaryExpr		{ BinaryExpr{} }-    ternaryExpr		{ TernaryExpr{} }-    assignExpr		{ AssignExpr{} }-    parenExpr		{ ParenExpr{} }-    castExpr		{ CastExpr{} }-    compoundExpr	{ CompoundExpr{} }-    sizeofExpr		{ SizeofExpr{} }-    sizeofType		{ SizeofType{} }-    literalExpr		{ LiteralExpr{} }-    varExpr		{ VarExpr{} }-    memberAccess	{ MemberAccess{} }-    pointerAccess	{ PointerAccess{} }-    arrayAccess		{ ArrayAccess{} }-    functionCall	{ FunctionCall{} }-    commentExpr		{ CommentExpr{} }+    initialiserList	{ Fix (InitialiserList{}) }+    unaryExpr		{ Fix (UnaryExpr{}) }+    binaryExpr		{ Fix (BinaryExpr{}) }+    ternaryExpr		{ Fix (TernaryExpr{}) }+    assignExpr		{ Fix (AssignExpr{}) }+    parenExpr		{ Fix (ParenExpr{}) }+    castExpr		{ Fix (CastExpr{}) }+    compoundExpr	{ Fix (CompoundExpr{}) }+    sizeofExpr		{ Fix (SizeofExpr{}) }+    sizeofType		{ Fix (SizeofType{}) }+    literalExpr		{ Fix (LiteralExpr{}) }+    varExpr		{ Fix (VarExpr{}) }+    memberAccess	{ Fix (MemberAccess{}) }+    pointerAccess	{ Fix (PointerAccess{}) }+    arrayAccess		{ Fix (ArrayAccess{}) }+    functionCall	{ Fix (FunctionCall{}) }+    commentExpr		{ Fix (CommentExpr{}) }     -- Type definitions-    enumClass		{ EnumClass{} }-    enumConsts		{ EnumConsts{} }-    enumDecl		{ EnumDecl{} }-    enumerator		{ Enumerator{} }-    classForward	{ ClassForward{} }-    typedef		{ Typedef{} }-    typedefFunction	{ TypedefFunction{} }-    struct		{ Struct{} }-    union		{ Union{} }-    memberDecl		{ MemberDecl{} }-    tyConst		{ TyConst{} }-    tyPointer		{ TyPointer{} }-    tyStruct		{ TyStruct{} }-    tyFunc		{ TyFunc{} }-    tyStd		{ TyStd{} }-    tyVar		{ TyVar{} }-    tyUserDefined	{ TyUserDefined{} }+    enumConsts		{ Fix (EnumConsts{}) }+    enumDecl		{ Fix (EnumDecl{}) }+    enumerator		{ Fix (Enumerator{}) }+    typedef		{ Fix (Typedef{}) }+    typedefFunction	{ Fix (TypedefFunction{}) }+    struct		{ Fix (Struct{}) }+    union		{ Fix (Union{}) }+    memberDecl		{ Fix (MemberDecl{}) }+    tyConst		{ Fix (TyConst{}) }+    tyPointer		{ Fix (TyPointer{}) }+    tyStruct		{ Fix (TyStruct{}) }+    tyFunc		{ Fix (TyFunc{}) }+    tyStd		{ Fix (TyStd{}) }+    tyUserDefined	{ Fix (TyUserDefined{}) }     -- Functions-    functionDecl	{ FunctionDecl{} }-    functionDefn	{ FunctionDefn{} }-    functionPrototype	{ FunctionPrototype{} }-    functionParam	{ FunctionParam{} }-    event		{ Event{} }-    eventParams		{ EventParams{} }-    property		{ Property{} }-    accessor		{ Accessor{} }-    errorDecl		{ ErrorDecl{} }-    errorList		{ ErrorList{} }-    errorFor		{ ErrorFor{} }-    ellipsis		{ Ellipsis }+    functionDecl	{ Fix (FunctionDecl{}) }+    functionDefn	{ Fix (FunctionDefn{}) }+    functionPrototype	{ Fix (FunctionPrototype{}) }+    functionParam	{ Fix (FunctionParam{}) }+    ellipsis		{ Fix (Ellipsis) }     -- Constants-    constDecl		{ ConstDecl{} }-    constDefn		{ ConstDefn{} }+    constDecl		{ Fix (ConstDecl{}) }+    constDefn		{ Fix (ConstDefn{}) }  %% @@ -189,7 +177,7 @@ Decl :	comment							{ $1 } |	CommentableDecl						{ $1 }-|	docComment CommentableDecl				{ Commented $1 $2 }+|	docComment CommentableDecl				{ Fix $ Commented $1 $2 }  CommentableDecl :: { TextNode } CommentableDecl@@ -214,7 +202,7 @@  { type TextLexeme = Lexeme Text-type TextNode = Node () TextLexeme+type TextNode = Node TextLexeme  newtype TreeParser a = TreeParser { toEither :: Either String a }     deriving (Functor, Applicative, Monad)@@ -224,41 +212,41 @@   isDefine :: [TextNode] -> Bool-isDefine (PreprocUndef{}:d)     = isDefine d-isDefine [PreprocDefine{}]      = True-isDefine [PreprocDefineConst{}] = True-isDefine _                      = False+isDefine (Fix PreprocUndef{}:d)     = isDefine d+isDefine [Fix PreprocDefine{}]      = True+isDefine [Fix PreprocDefineConst{}] = True+isDefine _                          = False  isPreproc :: TextNode -> Bool-isPreproc PreprocInclude{}        = True-isPreproc PreprocUndef{}          = True-isPreproc PreprocDefine{}         = True-isPreproc PreprocDefineConst{}    = True-isPreproc (PreprocIf _ td ed)     = all isPreproc td && isPreproc ed-isPreproc (PreprocIfdef _ td ed)  = all isPreproc td && isPreproc ed-isPreproc (PreprocIfndef _ td ed) = all isPreproc td && isPreproc ed-isPreproc (PreprocElse ed)        = all isPreproc ed-isPreproc _                       = False+isPreproc (Fix PreprocInclude{})        = True+isPreproc (Fix PreprocUndef{})          = True+isPreproc (Fix PreprocDefine{})         = True+isPreproc (Fix PreprocDefineConst{})    = True+isPreproc (Fix (PreprocIf _ td ed))     = all isPreproc td && isPreproc ed+isPreproc (Fix (PreprocIfdef _ td ed))  = all isPreproc td && isPreproc ed+isPreproc (Fix (PreprocIfndef _ td ed)) = all isPreproc td && isPreproc ed+isPreproc (Fix (PreprocElse ed))        = all isPreproc ed+isPreproc _                             = False  hasInclude :: TextNode -> Bool-hasInclude PreprocInclude{}        = True-hasInclude (PreprocIf _ td ed)     = any hasInclude td || hasInclude ed-hasInclude (PreprocIfdef _ td ed)  = any hasInclude td || hasInclude ed-hasInclude (PreprocIfndef _ td ed) = any hasInclude td || hasInclude ed-hasInclude (PreprocElse ed)        = any hasInclude ed-hasInclude _                       = False+hasInclude (Fix PreprocInclude{})        = True+hasInclude (Fix (PreprocIf _ td ed))     = any hasInclude td || hasInclude ed+hasInclude (Fix (PreprocIfdef _ td ed))  = any hasInclude td || hasInclude ed+hasInclude (Fix (PreprocIfndef _ td ed)) = any hasInclude td || hasInclude ed+hasInclude (Fix (PreprocElse ed))        = any hasInclude ed+hasInclude _                             = False   recurse :: ([TextNode] -> TreeParser [TextNode]) -> TextNode -> TreeParser TextNode-recurse f (ExternC ds)          = ExternC <$> f ds-recurse f (PreprocIf c t e)     = PreprocIf c <$> f t <*> recurse f e-recurse f (PreprocIfdef c t e)  = PreprocIfdef c <$> f t <*> recurse f e-recurse f (PreprocIfndef c t e) = PreprocIfndef c <$> f t <*> recurse f e-recurse f (PreprocIfndef c t e) = PreprocIfndef c <$> f t <*> recurse f e-recurse f (PreprocElif c t e)   = PreprocElif c <$> f t <*> recurse f e-recurse f (PreprocElse [])      = return $ PreprocElse []-recurse f (PreprocElse e)       = PreprocElse <$> f e-recurse _ ns                    = fail $ show ns+recurse f (Fix (ExternC ds))          = Fix <$> (ExternC <$> f ds)+recurse f (Fix (PreprocIf c t e))     = Fix <$> (PreprocIf c <$> f t <*> recurse f e)+recurse f (Fix (PreprocIfdef c t e))  = Fix <$> (PreprocIfdef c <$> f t <*> recurse f e)+recurse f (Fix (PreprocIfndef c t e)) = Fix <$> (PreprocIfndef c <$> f t <*> recurse f e)+recurse f (Fix (PreprocIfndef c t e)) = Fix <$> (PreprocIfndef c <$> f t <*> recurse f e)+recurse f (Fix (PreprocElif c t e))   = Fix <$> (PreprocElif c <$> f t <*> recurse f e)+recurse f (Fix (PreprocElse []))      = return $ Fix $ PreprocElse []+recurse f (Fix (PreprocElse e))       = Fix <$> (PreprocElse <$> f e)+recurse _ ns                          = fail $ "TreeParser.recurse: " <> show ns   parseError :: ([TextNode], [String]) -> TreeParser a
test/Language/Cimple/PrettySpec.hs view
@@ -35,8 +35,7 @@         it "pretty-prints a simple C function" $ do             let pp = pretty "int a(void) { return 3; }"             pp `shouldBe` unlines-                [ "int a(void)"-                , "{"+                [ "int a(void) {"                 , "  return 3;"                 , "}"                 ]@@ -53,8 +52,7 @@         it "pretty-prints a simple C function" $ do             let pp = compact "int a(void) { return 3; }"             pp `shouldBe` unlines-                [ "int a(void)"-                , "{"+                [ "int a(void) {"                 , "return 3;"                 , "}"                 ]@@ -93,18 +91,13 @@             compact "void foo(int const *a);"                 `shouldBe` "void foo(int const* a);\n" -        it "supports type-variables" $ do-            compact "void foo(`a a);" `shouldBe` "void foo(`a a);\n"-            compact "`a id(const `a a) { return a; }"-                `shouldBe` "`a id(`a const a)\n{\nreturn a;\n}\n"-         it "formats expressions and statements" $ do             compact "void foo() { return 1+2*3/4; }"-                `shouldBe` "void foo()\n{\nreturn 1 + 2 * 3 / 4;\n}\n"+                `shouldBe` "void foo() {\nreturn 1 + 2 * 3 / 4;\n}\n"             compact "void foo() { a = ~b << !c; }"-                `shouldBe` "void foo()\n{\na = ~b << !c;\n}\n"+                `shouldBe` "void foo() {\na = ~b << !c;\n}\n"             compact "void foo() { int a[] = {1,2,3}; }"-                `shouldBe` "void foo()\n{\nint a[] = { 1, 2, 3 };\n}\n"+                `shouldBe` "void foo() {\nint a[] = { 1, 2, 3 };\n}\n"          it "supports variadic functions" $ do             compact "void foo(int a, ...);"
test/Language/CimpleSpec.hs view
@@ -1,105 +1,94 @@ {-# LANGUAGE OverloadedStrings #-} module Language.CimpleSpec where -import           Data.Text          (Text)-import qualified Data.Text          as Text+import           Data.Fix           (Fix (..)) import           Test.Hspec         (Spec, describe, it, shouldBe)  import           Language.Cimple    (AlexPosn (..), CommentStyle (..),                                      Lexeme (..), LexemeClass (..),-                                     LiteralType (..), Node (..), Scope (..),-                                     TextActions, mapAst, textActions)+                                     LiteralType (..), NodeF (..), Scope (..)) import           Language.Cimple.IO (parseText)   spec :: Spec spec = do-    describe "TraverseAst" $ do-        it "should map the same way as mapM" $ do-            let Right ast = parseText "int a(void) { return 3; }"-            let actions :: TextActions Maybe () Text String-                actions = textActions (Just . Text.unpack)-            mapM (mapM (mapM (Just . Text.unpack))) ast-                `shouldBe`-                mapAst actions ast-     describe "C parsing" $ do         it "should parse a simple function" $ do             let ast = parseText "int a(void) { return 3; }"             ast `shouldBe` Right-                [ FunctionDefn+                [ Fix (FunctionDefn                       Global-                      (FunctionPrototype-                          (TyStd (L (AlexPn 0 1 1) IdStdType "int"))+                      (Fix (FunctionPrototype+                          (Fix (TyStd (L (AlexPn 0 1 1) IdStdType "int")))                           (L (AlexPn 4 1 5) IdVar "a")-                          [TyStd (L (AlexPn 6 1 7) KwVoid "void")]-                      )-                      [ Return+                          [Fix (TyStd (L (AlexPn 6 1 7) KwVoid "void"))]+                      ))+                      (Fix (CompoundStmt [ Fix (Return                             (Just-                                (LiteralExpr+                                (Fix (LiteralExpr                                     Int                                     (L (AlexPn 21 1 22) LitInteger "3")-                                )-                            )-                      ]+                                ))+                            ))+                      ])))                 ]          it "should parse a type declaration" $ do             let ast = parseText "typedef struct Foo { int x; } Foo;"             ast `shouldBe` Right-                [ Typedef-                      (Struct+                [ Fix (Typedef+                      (Fix (Struct                           (L (AlexPn 15 1 16) IdSueType "Foo")-                          [ MemberDecl-                                (TyStd (L (AlexPn 21 1 22) IdStdType "int"))-                                (DeclSpecVar (L (AlexPn 25 1 26) IdVar "x"))-                                Nothing+                          [ Fix (MemberDecl+                                (Fix (TyStd (L (AlexPn 21 1 22) IdStdType "int")))+                                (Fix (DeclSpecVar (L (AlexPn 25 1 26) IdVar "x")))+                                Nothing)                           ]-                      )-                      (L (AlexPn 30 1 31) IdSueType "Foo")+                      ))+                      (L (AlexPn 30 1 31) IdSueType "Foo"))                 ]          it "should parse a struct with bit fields" $ do             let ast = parseText "typedef struct Foo { int x : 123; } Foo;"             ast `shouldBe` Right-                [ Typedef-                      (Struct+                [ Fix (Typedef+                      (Fix (Struct                           (L (AlexPn 15 1 16) IdSueType "Foo")-                          [ MemberDecl-                                (TyStd (L (AlexPn 21 1 22) IdStdType "int"))-                                (DeclSpecVar (L (AlexPn 25 1 26) IdVar "x"))-                                (Just (L (AlexPn 29 1 30) LitInteger "123"))+                          [ Fix (MemberDecl+                                (Fix (TyStd (L (AlexPn 21 1 22) IdStdType "int")))+                                (Fix (DeclSpecVar (L (AlexPn 25 1 26) IdVar "x")))+                                (Just (L (AlexPn 29 1 30) LitInteger "123")))                           ]-                      )-                      (L (AlexPn 36 1 37) IdSueType "Foo")+                      ))+                      (L (AlexPn 36 1 37) IdSueType "Foo"))                 ]          it "should parse a comment" $ do             let ast = parseText "/* hello */"             ast `shouldBe` Right-                [ Comment Regular+                [ Fix (Comment Regular                           (L (AlexPn 0 1 1) CmtStart "/*")-                          [CommentWord (L (AlexPn 3 1 4) CmtWord "hello")]-                          (L (AlexPn 9 1 10) CmtEnd "*/")+                          [L (AlexPn 3 1 4) CmtWord "hello"]+                          (L (AlexPn 9 1 10) CmtEnd "*/"))                 ]          it "supports single declarators" $ do             let ast = parseText "int main() { int a; }"             ast `shouldBe` Right-                [ FunctionDefn+                [ Fix (FunctionDefn                       Global-                      (FunctionPrototype-                          (TyStd (L (AlexPn 0 1 1) IdStdType "int"))+                      (Fix (FunctionPrototype+                          (Fix (TyStd (L (AlexPn 0 1 1) IdStdType "int")))                           (L (AlexPn 4 1 5) IdVar "main")                           []-                      )-                      [ VarDecl-                            (TyStd (L (AlexPn 13 1 14) IdStdType "int"))-                            (Declarator-                                (DeclSpecVar (L (AlexPn 17 1 18) IdVar "a"))+                      ))+                      (Fix (CompoundStmt [ Fix (VarDecl+                            (Fix (TyStd (L (AlexPn 13 1 14) IdStdType "int")))+                            (Fix (Declarator+                                (Fix (DeclSpecVar (L (AlexPn 17 1 18) IdVar "a")))                                 Nothing-                            )-                      ]+                            )))+                      ])))                 ]          it "does not support multiple declarators per declaration" $ do