HORIZON HASKELLDocslts/ghc-9.10.x248f8f02026-10-05Search names, modules, packages, or :: a typeCtrl K

GHC 9.10.3 · lts/ghc-9.10.x · 248f8f0 · 2026-10-05

Modulelanguage-c-0.9.3Haskell2010

Language.C.Syntax.AST

Abstract syntax of C source and header files.

The tree structure is based on the grammar in Appendix A of K&R. The abstract syntax simplifies the concrete syntax by merging similar concrete constructs into a single type of abstract tree structure: declarations are merged with structure declarations, parameter declarations and type names, and declarators are merged with abstract declarators.

With K&R we refer to ``The C Programming Language'', second edition, Brain W. Kernighan and Dennis M. Ritchie, Prentice Hall, 1988. The AST supports all of C99 http://www.open-std.org/JTC1/SC22/WG14/www/docs/n1256.pdf and several GNU extensions http://gcc.gnu.org/onlinedocs/gcc/C-Extensions.html.

  • 58 types
  • 1 class
  • 4 values
  • Packagelanguage-c-0.9.3
  • Exports63
  • LanguageHaskell2010
  • LicenceBSD-3-Clause
  • SourceAST.hs

C translation units

4 declarations

Complete C tranlsation unit (C99 6.9, K&R A10)

A complete C translation unit, for example representing a C header or source file. It consists of a list of external (i.e. toplevel) declarations.

datadata CTranslationUnit a
#
Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CExternalDeclaration a
#
Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …

Declarations

9 declarations

C function definition (C99 6.9.1, K&R A10.1)

A function definition is of the form CFunDef specifiers declarator decllist? stmt.

  • specifiers are the type and storage-class specifiers of the function. The only storage-class specifiers allowed are extern and static.

  • The declarator must be such that the declared identifier has function type. The return type shall be void or an object type other than array type.

  • The optional declaration list decllist is for old-style function declarations.

  • The statement stmt is a compound statement.

typetype CDecl = CDeclaration NodeInfo
#

C declarations (K&R A8, C99 6.7), including structure declarations, parameter declarations and type names.

A declaration is of the form CDecl specifiers init-declarator-list, where the form of the declarator list's elements depends on the kind of declaration:

1) Toplevel declarations (K&R A8, C99 6.7 declaration)

  • C99 requires that there is at least one specifier, though this is merely a syntactic restriction

  • at most one storage class specifier is allowed per declaration

  • the elements of the non-empty init-declarator-list are of the form (Just declr, init?, Nothing). The declarator declr has to be present and non-abstract and the initialization expression is optional.

2) Structure declarations (K&R A8.3, C99 6.7.2.1 struct-declaration)

Those are the declarations of a structure's members.

  • do not allow storage specifiers

  • in strict C99, the list of declarators has to be non-empty

  • the elements of init-declarator-list are either of the form (Just declr, Nothing, size?), representing a member with optional bit-field size, or of the form (Nothing, Nothing, Just size), for unnamed bitfields. declr has to be non-abstract.

  • no member of a structure shall have incomplete type

3) Parameter declarations (K&R A8.6.3, C99 6.7.5 parameter-declaration)

  • init-declarator-list must contain at most one triple of the form (Just declr, Nothing, Nothing), i.e. consist of a single declarator, which is allowed to be abstract (i.e. unnamed).

4) Type names (A8.8, C99 6.7.6)

  • do not allow storage specifiers

  • init-declarator-list must contain at most one triple of the form (Just declr, Nothing, Nothing). where declr is an abstract declarator (i.e. doesn't contain a declared identifier)

C structure or union specifiers (K&R A8.3, C99 6.7.2.1)

CStruct tag identifier struct-decls c-attrs represents a struct or union specifier (depending on tag).

  • either identifier or the declaration list struct-decls (or both) have to be present.

Example: in struct foo x;, the identifier is present, in struct { int y; } x the declaration list, and in struct foo { int y; } x; both of them.

  • c-attrs is a list of attribute annotations associated with the struct or union specifier

typetype CEnum = CEnumeration NodeInfo
#

C enumeration specifier (K&R A8.4, C99 6.7.2.2)

CEnum identifier enumerator-list attrs represent as enum specifier

  • Either the identifier or the enumerator-list (or both) have to be present.

  • If enumerator-list is present, it has to be non-empty.

  • The enumerator list is of the form (enumeration-constant, enumeration-value?), where the latter is an optional constant integral expression.

  • attrs is a list of attribute annotations associated with the enumeration specifier

datadata CFunctionDef a
#
Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CDeclaration a
#
Instances10Functor, Pretty, Annotated, Data, Show, Generic, …
datadata CStructTag
#

A tag to determine wheter we refer to a struct or union, see CStructUnion.

Instances7Eq, Data, Show, Generic, NFData, Pretty, …
datadata CStructureUnion a
#
Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CEnumeration a
#

Constructors

Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …

Declaration attributes

16 declarations

C declaration specifiers and qualifiers

Declaration specifiers include at most one storage-class specifier (C99 6.7.1), type specifiers (6.7.2) and type qualifiers (6.7.3).

C type specifier (K&R A8.2, C99 6.7.2)

Type specifiers are either basic types such as char or int, struct, union or enum specifiers or typedef names.

As a GNU extension, a typeof expression also is a type specifier.

C type qualifiers (K&R A8.2, C99 6.7.3) and attributes.

const, volatile and restrict type qualifiers Additionally, attribute annotations for declarations and declarators, and function specifiers

typetype CAttr = CAttribute NodeInfo
#

attribute annotations

Those are of the form CAttr attribute-name attribute-parameters, and serve as generic properties of some syntax tree elements.

datadata CFunctionSpecifier a
#

Constructors

Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CDeclarationSpecifier a
#

Constructors

Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CStorageSpecifier a
#

Constructors

Instances14Functor, Pretty, Annotated, Generic1, Eq, Data, …
datadata CTypeSpecifier a
#

Constructors

Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CAlignmentSpecifier a
#

Constructors

Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CTypeQualifier a
#
Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CAttribute a
#

Constructors

Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …

Declarators

6 declarations
typetype CDeclr = CDeclarator NodeInfo
#

C declarator (K&R A8.5, C99 6.7.5) and abstract declarator (K&R A8.8, C99 6.7.6)

A declarator declares a single object, function, or type. It is always associated with a declaration (CDecl), which specifies the declaration's type and the additional storage qualifiers and attributes, which apply to the declared object.

A declarator is of the form CDeclr name? indirections asm-name? attrs _, where name is the name of the declared object (missing for abstract declarators), declquals is a set of additional declaration specifiers, asm-name is the optional assembler name and attributes is a set of attrs is a set of attribute annotations for the declared object.

indirections is a set of pointer, array and function declarators, which modify the type of the declared object as described below. If the declaration specifies the non-derived type T, and we have indirections = [D1, D2, ..., Dn] than the declared object has type (D1 indirect (D2 indirect ... (Dn indirect T))), where

  • (CPtrDeclr attrs) indirect T is attributed pointer to T

  • (CFunDeclr attrs) indirect T is attributed function returning T

  • (CArrayDeclr attrs) indirect T is attributed array of elemements of type T

Examples (simplified attributes):

  • x is an int

int x;
CDeclr "x" []
  • x is a restrict pointer to a const pointer to int

const int * const * restrict x;
CDeclr "x" [CPtrDeclr [restrict], CPtrDeclr [const]]
  • f is an function return a constant pointer to int

int* const f();
CDeclr "f" [CFunDeclr [],CPtrDeclr [const]]
  • f is a constant pointer to a function returning int

int (* const f)(); ==>
CDeclr "f" [CPtrDeclr [const], CFunDeclr []]

Derived declarators, see CDeclr

Indirections are qualified using type-qualifiers and generic attributes, and additionally

  • The size of an array is either a constant expression, variable length (*) or missing; in the last case, the type of the array is incomplete. The qualifier static is allowed for function arguments only, indicating that the supplied argument is an array of at least the given size.

  • New style parameter lists have the form Right (declarations, isVariadic), old style parameter lists have the form Left (parameter-names)

datadata CDeclarator a
#
Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CDerivedDeclarator a
#

Constructors

Instances9Functor, Annotated, Data, Show, Generic, NFData, …
datadata CArraySize a
#

Constructors

Instances9Functor, Pretty, Generic1, Data, Show, Generic, …

Initialization

6 declarations
typetype CInit = CInitializer NodeInfo
#

C initialization (K&R A8.7, C99 6.7.8)

Initializers are either assignment expressions or initializer lists (surrounded in curly braces), whose elements are themselves initializers, paired with an optional list of designators.

Initializer List

The members of an initializer list are of the form (designator-list,initializer). The designator-list specifies one member of the compound type which is initialized. It is allowed to be empty - in this case the initializer refers to the 'next' member of the compound type (see C99 6.7.8).

Examples (simplified expressions and identifiers):

-- int x[3][4] = { [0][3] = 4, [2] = 5, 8 };
--   corresponds to the assignments
-- x[0][3] = 4; x[2][0] = 5; x[2][1] = 8;
let init1 = ([CArrDesig 0, CArrDesig 3], CInitExpr 4)
    init2 = ([CArrDesig 2]             , CInitExpr 5)
    init3 = ([]                        , CInitExpr 8)
in  CInitList [init1, init2, init3]
-- struct { struct { int a[2]; int b[2]; int c[2]; } s; } x = { .s = { {2,3} , .c[0] = 1 } };
--   corresponds to the assignments
-- x.s.a[0] = 2; x.s.a[1] = 3; x.s.c[0] = 1;
let init_s_0 = CInitList [ ([], CInitExpr 2), ([], CInitExpr 3)]
    init_s   = CInitList [
                           ([], init_s_0),
                           ([CMemberDesig "c", CArrDesig 0], CInitExpr 1)
                         ]
in  CInitList [(CMemberDesig "s", init_s)]

Designators

A designator specifies a member of an object, either an element or range of an array, or the named member of a struct / union.

datadata CInitializer a
#

Constructors

Instances10Functor, Pretty, Annotated, Data, Show, Generic, …
datadata CPartDesignator a
#

Constructors

Instances10Functor, Pretty, Annotated, Data, Show, Generic, …

Statements

8 declarations

GNU Assembler statement

CAssemblyStatement type-qual? asm-expr out-ops in-ops clobbers _

is an inline assembler statement. The only type-qualifier (if any) allowed is volatile. asm-expr is the actual assembler epxression (a string), out-ops and in-ops are the input and output operands of the statement. clobbers is a list of registers which are clobbered when executing the assembler statement

datadata CStatement a
#

Constructors

Instances10Functor, Pretty, Annotated, Data, Show, Generic, …
datadata CCompoundBlockItem a
#

Constructors

Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CAssemblyStatement a
#
Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CAssemblyOperand a
#
Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …

Expressions

7 declarations
typetype CExpr = CExpression NodeInfo
#

C expression (K&R A7)

  • these can be arbitrary expression, as the argument of sizeof can be arbitrary, even if appearing in a constant expression

  • GNU C extensions: alignof, __real, __imag, ({ stmt-expr }), && label and built-ins

datadata CExpression a
#
Instances10Functor, Pretty, Annotated, Data, Show, Generic, …
datadata CAssignOp
#

C assignment operators (K&R A7.17)

Instances8Eq, Data, Ord, Show, Generic, NFData, …
datadata CBinaryOp
#

C binary operators (K&R A7.6-15)

Constructors

Instances8Eq, Data, Ord, Show, Generic, NFData, …
datadata CUnaryOp
#

C unary operator (K&R A7.3-4)

Constructors

Instances8Eq, Data, Ord, Show, Generic, NFData, …
datadata CBuiltinThing a
#

Constructors

Instances10Functor, Pretty, Annotated, Data, Show, Generic, …

Constants

6 declarations
datadata CConstant a
#
Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …
datadata CStringLiteral a
#

Constructors

Instances12Functor, Pretty, Annotated, Generic1, Data, Show, …

Annoated type class

1 declaration
classclass Functor ast => Annotated (ast :: Type -> Type) where
#

All AST nodes are annotated. Inspired by the Annotated class of Niklas Broberg's haskell-src-exts package. In principle, we could have Copointed superclass instead of ann, for the price of another dependency.

Methods

  • annotation :: ast a -> a

    get the annotation of an AST node

  • amap :: (a -> a) -> ast a -> ast a

    change the annotation (non-recursively) of an AST node. Use fmap for recursively modifying the annotation.

Instances25Annotated, …