# dmd.mtype

Defines a D type.

#### Authors

Walter Bright

#### License

Boost License 1.0

Source: mtype.d

Documentation: https://dlang.org/phobos/dmd_mtype.html

Coverage: https://codecov.io/gh/dlang/dmd/src/master/src/dmd/mtype.d

- `MODimplicitConv`

  #### Declaration

  `pure nothrow @nogc @safe bool `MODimplicitConv`(MOD `modfrom`, MOD `modto`);`

  Return !=0 if `modfrom` can be implicitly converted to `modto`

- `MODmethodConv`

  #### Declaration

  `pure nothrow @nogc @safe MATCH `MODmethodConv`(MOD `modfrom`, MOD `modto`);`

  Return MATCH.exact or MATCH.constant if a method of type '() `modfrom`' can call a method of type '() `modto`'.

- `MODmerge`

  #### Declaration

  `pure nothrow @nogc @safe MOD `MODmerge`(MOD `mod1`, MOD `mod2`);`

  Merge mod bits to form common mod.

- `MODtoBuffer`

  #### Declaration

  `nothrow void `MODtoBuffer`(OutBuffer* `buf`, MOD `mod`);`

  Store modifier name into `buf`.

- `MODtoChars`

  #### Declaration

  `pure nothrow const(char)* `MODtoChars`(MOD `mod`);
  pure nothrow string `MODtoString`(MOD `mod`);`

  #### Return Value

  a human readable representation of ``mod``, which is the token ``mod`` corresponds to

- `ModToStc`

  #### Declaration

  `pure nothrow @nogc @safe StorageClass `ModToStc`(uint `mod`);`

  Convert MODxxxx to STCxxx

- `isSomeChar`

  #### Declaration

  `pure nothrow @nogc @safe bool `isSomeChar`(TY `ty`);`

  Returns `true` if `ty` is char, wchar, or dchar

- `DotExpFlag`

  #### Declaration

  `enum `DotExpFlag`: int;`

  dotExp() bit flags

- `VarArg`

  #### Declaration

  `enum `VarArg`: ubyte;`

  Variadic argument lists https://dlang.org/spec/function.html#variadic

  - `none`

    #### Declaration

    ``none``

    fixed number of arguments

  - `variadic`

    #### Declaration

    ``variadic``

    (T t, ...) can be C-style (core.stdc.stdarg) or D-style (core.vararg)

  - `typesafe`

    #### Declaration

    ``typesafe``

    (T t ...) `typesafe` https://dlang.org/spec/function.html#typesafe_variadic_functions

- `Type`

  #### Declaration

  `abstract class `Type`: dmd.ast_node.ASTNode;`

  - `covariant`

    #### Declaration

    `final int `covariant`(Type `t`, StorageClass* `pstc` = null);`

    Covariant means that 'this' can substitute for '`t`', i.e. a pure function is a match for an impure type.

    #### Parameters

    `Type `t`` | type 'this' is `covariant` with
    `StorageClass* `pstc`` | if not `null`, store STCxxxx which would make it `covariant`

    #### Return Value

    0 types are distinct 1 this is `covariant` with `t` 2 arguments match as far as overloading goes, but types are not `covariant` 3 cannot determine covariance because of forward references *`pstc` STCxxxx which would make it `covariant`

  - `toChars`

    #### Declaration

    `final const const(char)* `toChars`();
    final char* `toPrettyChars`(bool `QualifyTypes` = false);`

    For pretty-printing a type.

  - `deinitialize`

    #### Declaration

    `static void `deinitialize`();`

    Deinitializes the global state of the compiler.

    #### Discussion

    This can be used to restore the state set by `_init` to its original state.

  - `merge2`

    #### Declaration

    `final Type `merge2`();`

    This version does a merge even if the deco is already computed. Necessary for types that have a deco, but are not merged.

  - `modToBuffer`

    #### Declaration

    `final const nothrow void `modToBuffer`(OutBuffer* `buf`);`

    Store this type's modifier name into `buf`.

  - `modToChars`

    #### Declaration

    `final const nothrow char* `modToChars`();`

    Return this type's modifier name.

  - `isAssignable`

    #### Declaration

    `bool `isAssignable`();`

    When T is mutable,

    Given: T a, b; Can we bitwise assign: a = b; ?

  - `isBoolean`

    #### Declaration

    `bool `isBoolean`();`

    Returns `true` if T can be converted to boolean value.

  - `checkDeprecated`

    #### Declaration

    `void `checkDeprecated`(ref const Loc `loc`, Scope* `sc`);`

    Check type to see if it is based on a deprecated symbol.

  - `nullAttributes`

    #### Declaration

    `final const nothrow Type `nullAttributes`();`

    Return a copy of this type with all attributes `null`-initialized. Useful for creating a type with different modifiers.

  - `constOf`

    #### Declaration

    `final Type `constOf`();`

    Convert to 'const'.

  - `immutableOf`

    #### Declaration

    `final Type `immutableOf`();`

    Convert to 'immutable'.

  - `mutableOf`

    #### Declaration

    `final Type `mutableOf`();`

    Make type mutable.

  - `unSharedOf`

    #### Declaration

    `final Type `unSharedOf`();`

    Make type unshared. 0 => 0 const => const immutable => immutable shared => 0 shared const => const wild => wild wild const => wild const shared wild => wild shared wild const => wild const

  - `wildOf`

    #### Declaration

    `final Type `wildOf`();`

    Convert to 'wild'.

  - `fixTo`

    #### Declaration

    `final void `fixTo`(Type `t`);`

    For our new type 'this', which is type-constructed from `t`, fill in the cto, ito, sto, scto, wto shortcuts.

  - `check`

    #### Declaration

    `final void `check`();`

    Look for bugs in constructing types.

  - `addSTC`

    #### Declaration

    `final Type `addSTC`(StorageClass `stc`);`

    Apply STCxxxx bits to existing type. Use before semantic analysis is run.

  - `castMod`

    #### Declaration

    `final Type `castMod`(MOD `mod`);`

    Apply MODxxxx bits to existing type.

  - `addMod`

    #### Declaration

    `final Type `addMod`(MOD `mod`);`

    Add MODxxxx bits to existing type. We're adding, not replacing, so adding const to a shared type => "shared const"

  - `addStorageClass`

    #### Declaration

    `Type `addStorageClass`(StorageClass `stc`);`

    Add storage class modifiers to type.

  - `toBasetype`

    #### Declaration

    `final Type `toBasetype`();`

    If this is a shell around another type, get that other type.

  - `implicitConvTo`

    #### Declaration

    `MATCH `implicitConvTo`(Type `to`);`

    Determine if 'this' can be implicitly converted `to` type '`to`'.

    #### Return Value

    MATCH.nomatch, MATCH.convert, MATCH.constant, MATCH.exact

  - `constConv`

    #### Declaration

    `MATCH `constConv`(Type `to`);`

    Determine if converting 'this' `to` '`to`' is an identity operation, a conversion `to` const operation, or the types aren't the same.

    #### Return Value

    MATCH.exact 'this' == '`to`' MATCH.constant '`to`' is const MATCH.nomatch conversion `to` mutable or invariant

  - `deduceWild`

    #### Declaration

    `MOD `deduceWild`(Type `t`, bool `isRef`);`

    Compute MOD bits matching `this` argument type to wild parameter type.

    #### Parameters

    `Type `t`` | corresponding parameter type
    `bool `isRef`` | parameter is `ref` or `out`

    #### Return Value

    MOD bits

  - `toHeadMutable`

    #### Declaration

    `inout inout(Type) `toHeadMutable`();`

    Return type with the top level of it being mutable.

  - `alignment`

    #### Declaration

    `structalign_t `alignment`();`

    Return `alignment` to use for this type.

  - `defaultInitLiteral`

    #### Declaration

    `Expression `defaultInitLiteral`(ref const Loc `loc`);`

    Use when we prefer the default initializer to be a literal, rather than a global immutable variable.

  - `hasWild`

    #### Declaration

    `const int `hasWild`();`

    Return !=0 if the type or any of its subtypes is wild.

  - `hasPointers`

    #### Declaration

    `bool `hasPointers`();`

    Return !=0 if type has pointers that need to be scanned by the GC during a collection cycle.

  - `hasVoidInitPointers`

    #### Declaration

    `bool `hasVoidInitPointers`();`

    Detect if type has pointer fields that are initialized to void. Local stack variables with such void fields can remain uninitialized, leading to pointer bugs.

    #### Return Value

    `true` if so

  - `nextOf`

    #### Declaration

    `Type `nextOf`();`

    If this is a type of something, return that something.

  - `baseElemOf`

    #### Declaration

    `final Type `baseElemOf`();`

    If this is a type of static array, return its base element type.

  - `numberOfElems`

    #### Declaration

    `final uint `numberOfElems`(ref const Loc `loc`);`

    Compute number of elements for a (possibly multidimensional) static array, or 1 for other types.

    #### Parameters

    `Loc `loc`` | for error message

    #### Return Value

    number of elements, uint.max on overflow

  - `sizemask`

    #### Declaration

    `final uinteger_t `sizemask`();`

    Return the mask that an integral type will fit into.

  - `needsDestruction`

    #### Declaration

    `bool `needsDestruction`();`

    `true` if when type goes out of scope, it needs a destructor applied. Only applies to value types, not ref types.

  - `needsCopyOrPostblit`

    #### Declaration

    `bool `needsCopyOrPostblit`();`

    `true` if when type is copied, it needs a copy constructor or postblit applied. Only applies to value types, not ref types.

  - `needsNested`

    #### Declaration

    `bool `needsNested`();`

  - `checkComplexTransition`

    #### Declaration

    `final bool `checkComplexTransition`(ref const Loc `loc`, Scope* `sc`);`

    https://issues.dlang.org/show_bug.cgi?id=14488 Check if the inner most base type is complex or imaginary. Should only give alerts when set to emit transitional messages.

    #### Parameters

    `Loc `loc`` | The source location.
    `Scope* `sc`` | scope of the type

- `TypeError`

  #### Declaration

  `class `TypeError`: dmd.mtype.Type;`

- `TypeNext`

  #### Declaration

  `abstract class `TypeNext`: dmd.mtype.Type;`

  - `nextOf`

    #### Declaration

    `final Type `nextOf`();`

    For TypeFunction, `nextOf`() can return NULL if the function return type is meant to be inferred, and semantic() hasn't yet ben run on the function. After semantic(), it must no longer be NULL.

- `TypeBasic`

  #### Declaration

  `class `TypeBasic`: dmd.mtype.Type;`

- `TypeVector`

  #### Declaration

  `class `TypeVector`: dmd.mtype.Type;`

  The basetype must be one of: byte[16],ubyte[16],short[8],ushort[8],int[4],uint[4],long[2],ulong[2],float[4],double[2] For AVX: byte[32],ubyte[32],short[16],ushort[16],int[8],uint[8],long[4],ulong[4],float[8],double[4]

- `TypeArray`

  #### Declaration

  `abstract class `TypeArray`: dmd.mtype.TypeNext;`

- `TypeSArray`

  #### Declaration

  `class `TypeSArray`: dmd.mtype.TypeArray;`

  Static array, one with a fixed dimension

  - `needsNested`

    #### Declaration

    `bool `needsNested`();`

- `TypeDArray`

  #### Declaration

  `class `TypeDArray`: dmd.mtype.TypeArray;`

  Dynamic array, no dimension

- `TypeAArray`

  #### Declaration

  `class `TypeAArray`: dmd.mtype.TypeArray;`

- `TypePointer`

  #### Declaration

  `class `TypePointer`: dmd.mtype.TypeNext;`

- `TypeReference`

  #### Declaration

  `class `TypeReference`: dmd.mtype.TypeNext;`

- `TypeFunction`

  #### Declaration

  `class `TypeFunction`: dmd.mtype.TypeNext;`

  - `purityLevel`

    #### Declaration

    `void `purityLevel`();`

    Set 'purity' field of 'this'. Do this lazily, as the parameter types might be forward referenced.

  - `hasLazyParameters`

    #### Declaration

    `bool `hasLazyParameters`();`

    Return `true` if there are lazy parameters.

  - `isDstyleVariadic`

    #### Declaration

    `const pure nothrow bool `isDstyleVariadic`();`

    Check for `extern (D) U func(T t, ...)` variadic function type, which has `_arguments[]` added as the first argument.

    #### Return Value

    `true` if D-style variadic

  - `parameterEscapes`

    #### Declaration

    `bool `parameterEscapes`(Type `tthis`, Parameter `p`);`

    Examine function signature for parameter `p` and see if the value of `p` can 'escape' the scope of the function. This is useful to minimize the needed annotations for the parameters.

    #### Parameters

    `Type `tthis`` | type of `this` parameter, `null` if none
    `Parameter `p`` | parameter to this function

    #### Return Value

    `true` if escapes via assignment to global or through a parameter

  - `parameterStorageClass`

    #### Declaration

    `StorageClass `parameterStorageClass`(Type `tthis`, Parameter `p`);`

    Take the specified storage class for `p`, and use the function signature to infer whether STC.scope_ and STC.return_ should be OR'd in. (This will not affect the name mangling.)

    #### Parameters

    `Type `tthis`` | type of `this` parameter, `null` if none
    `Parameter `p`` | parameter to this function

    #### Return Value

    storage class with STC.scope_ or STC.return_ OR'd in

  - `callMatch`

    #### Declaration

    `MATCH `callMatch`(Type `tthis`, Expression[] `args`, int `flag` = 0, const(char)** `pMessage` = null, Scope* `sc` = null);`

    '`args`' are being matched to function 'this' Determine match level.

    #### Parameters

    `Type `tthis`` | type of `this` pointer, `null` if not member function
    `Expression[] `args`` | array of function arguments
    `int `flag`` | 1: performing a partial ordering match
    `const(char)** `pMessage`` | address to store error message, or `null`
    `Scope* `sc`` | context

    #### Return Value

    MATCHxxxx

  - `constConv`

    #### Declaration

    `MATCH `constConv`(Type `to`);`

    Extends TypeNext.`constConv` by also checking for matching attributes

  - `isnothrow`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isnothrow`();
    pure nothrow @nogc @safe void `isnothrow`(bool `v`);`

    set or get if the function has the `nothrow` attribute

  - `isnogc`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isnogc`();
    pure nothrow @nogc @safe void `isnogc`(bool `v`);`

    set or get if the function has the `@nogc` attribute

  - `isproperty`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isproperty`();
    pure nothrow @nogc @safe void `isproperty`(bool `v`);`

    set or get if the function has the `@property` attribute

  - `isref`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isref`();
    pure nothrow @nogc @safe void `isref`(bool `v`);`

    set or get if the function has the `ref` attribute

  - `isreturn`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isreturn`();
    pure nothrow @nogc @safe void `isreturn`(bool `v`);`

    set or get if the function has the `return` attribute

  - `isScopeQual`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isScopeQual`();
    pure nothrow @nogc @safe void `isScopeQual`(bool `v`);`

    set or get if the function has the `scope` attribute

  - `isreturninferred`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isreturninferred`();
    pure nothrow @nogc @safe void `isreturninferred`(bool `v`);`

    set or get if the function has the `return` attribute inferred

  - `isscopeinferred`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isscopeinferred`();`

    set or get if the function has the `scope` attribute inferred

  - `isscopeinferred`

    #### Declaration

    `pure nothrow @nogc @safe void `isscopeinferred`(bool `v`);`

    ditoo

  - `islive`

    #### Declaration

    `const pure nothrow @nogc @safe bool `islive`();
    pure nothrow @nogc @safe void `islive`(bool `v`);`

    set or get if the function has the `@live` attribute

  - `incomplete`

    #### Declaration

    `const pure nothrow @nogc @safe bool `incomplete`();
    pure nothrow @nogc @safe void `incomplete`(bool `v`);`

    set or get if the return type or the default arguments are removed

  - `isInOutParam`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isInOutParam`();
    pure nothrow @nogc @safe void `isInOutParam`(bool `v`);`

    set or get if the function has the `inout` on the parameters

  - `isInOutQual`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isInOutQual`();
    pure nothrow @nogc @safe void `isInOutQual`(bool `v`);`

    set or get if the function has the `inout` on the parameters

  - `iswild`

    #### Declaration

    `const pure nothrow @nogc @safe bool `iswild`();`

    #### Return Value

    `true` the function is `isInOutQual` or `isInOutParam` ,`false` otherwise.

  - `attributesEqual`

    #### Declaration

    `const pure nothrow @nogc @safe bool `attributesEqual`(scope const TypeFunction `other`);`

    #### Return Value

    whether `this` function type has the same attributes (`@safe`,...) as ``other``

- `TypeDelegate`

  #### Declaration

  `class `TypeDelegate`: dmd.mtype.TypeNext;`

- `TypeTraits`

  #### Declaration

  `class `TypeTraits`: dmd.mtype.Type;`

  This is a shell containing a TraitsExp that can be either resolved to a type or to a symbol.

  #### Discussion

  The point is to allow AliasDeclarationY to use `__traits()`, see issue 7804.

  - `exp`

    #### Declaration

    `TraitsExp `exp`;`

    The expression to resolve as type or symbol.

  - `sym`

    #### Declaration

    `Dsymbol `sym`;`

    After `typeSemantic` the symbol when `exp` doesn't represent a type.

- `TypeMixin`

  #### Declaration

  `class `TypeMixin`: dmd.mtype.Type;`

  Implements mixin types.

  #### Discussion

  Semantic analysis will convert it to a real type.

- `TypeQualified`

  #### Declaration

  `abstract class `TypeQualified`: dmd.mtype.Type;`

- `TypeIdentifier`

  #### Declaration

  `class `TypeIdentifier`: dmd.mtype.TypeQualified;`

  - `toDsymbol`

    #### Declaration

    `Dsymbol `toDsymbol`(Scope* `sc`);`

    See if type resolves to a symbol, if so, return that symbol.

- `TypeInstance`

  #### Declaration

  `class `TypeInstance`: dmd.mtype.TypeQualified;`

  Similar to TypeIdentifier, but with a TemplateInstance as the root

- `TypeTypeof`

  #### Declaration

  `class `TypeTypeof`: dmd.mtype.TypeQualified;`

- `TypeReturn`

  #### Declaration

  `class `TypeReturn`: dmd.mtype.TypeQualified;`

- `TypeStruct`

  #### Declaration

  `class `TypeStruct`: dmd.mtype.Type;`

  - `defaultInitLiteral`

    #### Declaration

    `Expression `defaultInitLiteral`(ref const Loc `loc`);`

    Use when we prefer the default initializer to be a literal, rather than a global immutable variable.

- `TypeEnum`

  #### Declaration

  `class `TypeEnum`: dmd.mtype.Type;`

- `TypeClass`

  #### Declaration

  `class `TypeClass`: dmd.mtype.Type;`

- `TypeTuple`

  #### Declaration

  `class `TypeTuple`: dmd.mtype.Type;`

  - `this`

    #### Declaration

    `this(Expressions* `exps`);`

    Form TypeTuple from the types of the expressions. Assume `exps`[] is already tuple expanded.

  - `this`

    #### Declaration

    `this();`

    Type tuple with 0, 1 or 2 types in it.

- `TypeSlice`

  #### Declaration

  `class `TypeSlice`: dmd.mtype.TypeNext;`

  This is so we can slice a TypeTuple

- `TypeNull`

  #### Declaration

  `class `TypeNull`: dmd.mtype.Type;`

- `TypeNoreturn`

  #### Declaration

  `class `TypeNoreturn`: dmd.mtype.Type;`

- `ParameterList`

  #### Declaration

  `struct `ParameterList`;`

  Represents a function's formal parameters + variadics info. Length, indexing and iteration are based on a depth-first tuple expansion. https://dlang.org/spec/function.html#ParameterList

  - `parameters`

    #### Declaration

    `Parameters* `parameters`;`

    The raw (unexpanded) formal `parameters`, possibly containing tuples.

  - `length`

    #### Declaration

    `size_t `length`();`

    Returns the number of expanded parameters. Complexity: O(N).

  - `opIndex`

    #### Declaration

    `Parameter `opIndex`(size_t `i`);`

    Returns the expanded parameter at the given index, or `null` if out of bounds. Complexity: O(`i`).

  - `opApply`

    #### Declaration

    `int `opApply`(scope Parameter.ForeachDg `dg`);`

    Iterates over the expanded parameters. Complexity: O(N). Prefer this to avoid the O(N + N^2/2) complexity of calculating length and calling N times opIndex.

  - `opApply`

    #### Declaration

    `int `opApply`(scope Parameter.SemanticForeachDg `dg`);`

    Iterates over the expanded parameters, matching them with the unexpanded ones, for semantic processing

  - `opEquals`

    #### Declaration

    `const bool `opEquals`(ref scope ParameterList `other`);`

    Compares this to another ParameterList (and expands tuples if necessary)

- `Parameter`

  #### Declaration

  `class `Parameter`: dmd.ast_node.ASTNode;`

  - `isLazyArray`

    #### Declaration

    `Type `isLazyArray`();`

    Determine if parameter is a lazy array of delegates. If so, return the return type of those delegates. If not, return NULL.

    #### Discussion

    Returns T if the type is one of the following forms: T delegate()[] T delegate()`dim`

  - `isReference`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isReference`();`

    #### Return Value

    Whether the function parameter is a reference (out / ref)

  - `dim`

    #### Declaration

    `static size_t `dim`(Parameters* `parameters`);`

    Determine number of arguments, folding in tuples.

  - `getNth`

    #### Declaration

    `static Parameter `getNth`(Parameters* `parameters`, size_t `nth`);`

    Get `nth` `Parameter`, folding in tuples.

    #### Discussion

    Since ``parameters`` can include tuples, which would increase its length, this function allows to get the ``nth`` parameter as if all tuples transitively contained in ``parameters`` were flattened.

    #### Parameters

    `Parameters* `parameters`` | Array of `Parameter` to iterate over
    `size_t `nth`` | Index of the desired parameter.

    #### Return Value

    The parameter at index ``nth`` (taking tuples into account), or `null` if out of bound.

  - `ForeachDg`

    #### Declaration

    `alias `ForeachDg` = int delegate(ulong paramidx, Parameter param);`

    Type of delegate when iterating solely on the parameters

  - `SemanticForeachDg`

    #### Declaration

    `alias `SemanticForeachDg` = int delegate(ulong oidx, Parameter oparam, ulong eidx, Parameter eparam);`

    Type of delegate when iterating on both the original set of parameters, and the type tuple. Useful for semantic analysis. 'o' stands for 'original' and 'e' stands for 'expanded'.

  - `_foreach`

    #### Declaration

    `static int `_foreach`(Parameters* `parameters`, scope ForeachDg `dg`);
    static int `_foreach`(Parameters* `parameters`, scope SemanticForeachDg `dg`);`

    Expands tuples in args in depth first order. Calls `dg`(void *ctx, size_t argidx, Parameter *arg) for each Parameter. If `dg` returns !=0, stops and returns that value else returns 0. Use this function to avoid the O(N + N^2/2) complexity of calculating dim and calling N times getNth.

  - `isCovariant`

    #### Declaration

    `const pure nothrow @nogc @safe bool `isCovariant`(bool `returnByRef`, const Parameter `p`, bool `previewIn` = global.params.`previewIn`);`

    Compute covariance of parameters `this` and ``p`` as determined by the storage classes of both.

    #### Parameters

    `bool `returnByRef`` | `true` if the function returns by ref
    `Parameter `p`` | Parameter to compare with
    `bool `previewIn`` | Whether `-preview=in` is being used, and thus if `in` means `scope [ref]`.

    #### Return Value

    `true` = `this` can be used in place of ``p`` `false` = nope

- `toAutoQualChars`

  #### Declaration

  `const(char*)[2] `toAutoQualChars`(Type `t1`, Type `t2`);`

  For printing two types with qualification when necessary.

  #### Parameters

  `Type `t1`` | The first type to receive the type name for
  `Type `t2`` | The second type to receive the type name for

  #### Return Value

  The fully-qualified names of both types if the two type names are not the same, or the unqualified names of both types if the two type names are the same.

- `modifiersApply`

  #### Declaration

  `void `modifiersApply`(const TypeFunction `tf`, void delegate(string) `dg`);`

  For each active modifier (MODFlags.const_, MODFlags.immutable_, etc) call `fp` with a void* for the work param and a string representation of the attribute.

- `attributesApply`

  #### Declaration

  `void `attributesApply`(const TypeFunction `tf`, void delegate(string) `dg`, TRUSTformat `trustFormat` = TRUSTformatDefault);`

  For each active attribute (ref/const/nogc/etc) call `fp` with a void* for the work param and a string representation of the attribute.

- `isAggregate`

  #### Declaration

  `AggregateDeclaration `isAggregate`(Type `t`);`

  If the type is a class or struct, returns the symbol for it, else `null`.

- `isIndexableNonAggregate`

  #### Declaration

  `bool `isIndexableNonAggregate`(Type `t`);`

  Determine if type `t` can be indexed or sliced given that it is not an aggregate with operator overloads.

  #### Parameters

  `Type `t`` | type to check

  #### Return Value

  `true` if an expression of type `t` can be e1 in an array expression

- `isCopyable`

  #### Declaration

  `bool `isCopyable`(Type `t`);`

  Determine if type `t` is copyable.

  #### Parameters

  `Type `t`` | type to check

  #### Return Value

  `true` if we can copy it