(root)/
gcc-13.2.0/
gcc/
d/
dmd/
declaration.h
       1  
       2  /* Compiler implementation of the D programming language
       3   * Copyright (C) 1999-2023 by The D Language Foundation, All Rights Reserved
       4   * written by Walter Bright
       5   * https://www.digitalmars.com
       6   * Distributed under the Boost Software License, Version 1.0.
       7   * https://www.boost.org/LICENSE_1_0.txt
       8   * https://github.com/dlang/dmd/blob/master/src/dmd/declaration.h
       9   */
      10  
      11  #pragma once
      12  
      13  #include "dsymbol.h"
      14  #include "mtype.h"
      15  #include "objc.h"
      16  #include "tokens.h"
      17  
      18  class Expression;
      19  class Statement;
      20  class LabelDsymbol;
      21  class Initializer;
      22  class ForeachStatement;
      23  struct Ensure
      24  {
      25      Identifier *id;
      26      Statement *ensure;
      27  };
      28  class FuncDeclaration;
      29  class StructDeclaration;
      30  struct IntRange;
      31  struct AttributeViolation;
      32  
      33  //enum STC : ulong from astenums.d:
      34  
      35      #define STCundefined          0ULL
      36  
      37      #define STCstatic             1ULL    /// `static`
      38      #define STCextern             2ULL    /// `extern`
      39      #define STCconst              4ULL    /// `const`
      40      #define STCfinal              8ULL    /// `final`
      41  
      42      #define STCabstract           0x10ULL    /// `abstract`
      43      #define STCparameter          0x20ULL    /// is function parameter
      44      #define STCfield              0x40ULL    /// is field of struct, union or class
      45      #define STCoverride           0x80ULL    /// `override`
      46  
      47      #define STCauto               0x100ULL    /// `auto`
      48      #define STCsynchronized       0x200ULL    /// `synchronized`
      49      #define STCdeprecated         0x400ULL    /// `deprecated`
      50      #define STCin                 0x800ULL    /// `in` parameter
      51  
      52      #define STCout                0x1000ULL    /// `out` parameter
      53      #define STClazy               0x2000ULL    /// `lazy` parameter
      54      #define STCforeach            0x4000ULL    /// variable for foreach loop
      55      #define STCvariadic           0x8000ULL    /// the `variadic` parameter in: T foo(T a, U b, V variadic...)
      56  
      57      //                            0x10000ULL
      58      #define STCtemplateparameter  0x20000ULL    /// template parameter
      59      #define STCref                0x40000ULL    /// `ref`
      60      #define STCscope              0x80000ULL    /// `scope`
      61  
      62      #define STCscopeinferred      0x200000ULL    /// `scope` has been inferred and should not be part of mangling, `scope` must also be set
      63      #define STCreturn             0x400000ULL    /// 'return ref' or 'return scope' for function parameters
      64      #define STCreturnScope        0x800000ULL    /// if `ref return scope` then resolve to `ref` and `return scope`
      65  
      66      #define STCreturninferred     0x1000000ULL    /// `return` has been inferred and should not be part of mangling, `return` must also be set
      67      #define STCimmutable          0x2000000ULL    /// `immutable`
      68      //                            0x4000000ULL
      69      #define STCmanifest           0x8000000ULL    /// manifest constant
      70  
      71      #define STCnodtor             0x10000000ULL    /// do not run destructor
      72      #define STCnothrow            0x20000000ULL    /// `nothrow` meaning never throws exceptions
      73      #define STCpure               0x40000000ULL    /// `pure` function
      74  
      75      #define STCalias              0x100000000ULL    /// `alias` parameter
      76      #define STCshared             0x200000000ULL    /// accessible from multiple threads
      77      #define STCgshared            0x400000000ULL    /// accessible from multiple threads, but not typed as `shared`
      78      #define STCwild               0x800000000ULL    /// for wild type constructor
      79  
      80      #define STCproperty           0x1000000000ULL    /// `@property`
      81      #define STCsafe               0x2000000000ULL    /// `@safe`
      82      #define STCtrusted            0x4000000000ULL    /// `@trusted`
      83      #define STCsystem             0x8000000000ULL    /// `@system`
      84  
      85      #define STCctfe               0x10000000000ULL    /// can be used in CTFE, even if it is static
      86      #define STCdisable            0x20000000000ULL    /// for functions that are not callable
      87      #define STCresult             0x40000000000ULL    /// for result variables passed to out contracts
      88      #define STCnodefaultctor      0x80000000000ULL    /// must be set inside constructor
      89  
      90      #define STCtemp               0x100000000000ULL    /// temporary variable
      91      #define STCrvalue             0x200000000000ULL    /// force rvalue for variables
      92      #define STCnogc               0x400000000000ULL    /// `@nogc`
      93      #define STCautoref            0x800000000000ULL    /// Mark for the already deduced `auto ref` parameter
      94  
      95      #define STCinference          0x1000000000000ULL    /// do attribute inference
      96      #define STCexptemp            0x2000000000000ULL    /// temporary variable that has lifetime restricted to an expression
      97      #define STCfuture             0x4000000000000ULL    /// introducing new base class function
      98      #define STClocal              0x8000000000000ULL    /// do not forward (see dmd.dsymbol.ForwardingScopeDsymbol).
      99  
     100      #define STClive               0x10000000000000ULL    /// function `@live` attribute
     101      #define STCregister           0x20000000000000ULL    /// `register` storage class (ImportC)
     102      #define STCvolatile           0x40000000000000ULL    /// destined for volatile in the back end
     103  
     104  #define STC_TYPECTOR    (STCconst | STCimmutable | STCshared | STCwild)
     105  #define STC_FUNCATTR    (STCref | STCnothrow | STCnogc | STCpure | STCproperty | STCsafe | STCtrusted | STCsystem)
     106  
     107  void ObjectNotFound(Identifier *id);
     108  
     109  /**************************************************************/
     110  
     111  class Declaration : public Dsymbol
     112  {
     113  public:
     114      Type *type;
     115      Type *originalType;         // before semantic analysis
     116      StorageClass storage_class;
     117      Visibility visibility;
     118      LINK _linkage;              // may be `LINK::system`; use `resolvedLinkage()` to resolve it
     119      short inuse;                // used to detect cycles
     120      uint8_t adFlags;
     121      Symbol* isym;               // import version of csym
     122      DString mangleOverride;     // overridden symbol with pragma(mangle, "...")
     123  
     124      const char *kind() const override;
     125      uinteger_t size(const Loc &loc) override final;
     126  
     127      Dsymbol *search(const Loc &loc, Identifier *ident, int flags = SearchLocalsOnly) override final;
     128  
     129      bool isStatic() const { return (storage_class & STCstatic) != 0; }
     130      LINK resolvedLinkage() const; // returns the linkage, resolving the target-specific `System` one
     131      virtual bool isDelete();
     132      virtual bool isDataseg();
     133      virtual bool isThreadlocal();
     134      virtual bool isCodeseg() const;
     135      bool isFinal() const        { return (storage_class & STCfinal) != 0; }
     136      virtual bool isAbstract()   { return (storage_class & STCabstract) != 0; }
     137      bool isConst() const        { return (storage_class & STCconst) != 0; }
     138      bool isImmutable() const    { return (storage_class & STCimmutable) != 0; }
     139      bool isWild() const         { return (storage_class & STCwild) != 0; }
     140      bool isAuto() const         { return (storage_class & STCauto) != 0; }
     141      bool isScope() const        { return (storage_class & STCscope) != 0; }
     142      bool isReturn() const       { return (storage_class & STCreturn) != 0; }
     143      bool isSynchronized() const { return (storage_class & STCsynchronized) != 0; }
     144      bool isParameter() const    { return (storage_class & STCparameter) != 0; }
     145      bool isDeprecated() const override final { return (storage_class & STCdeprecated) != 0; }
     146      bool isOverride() const     { return (storage_class & STCoverride) != 0; }
     147      bool isResult() const       { return (storage_class & STCresult) != 0; }
     148      bool isField() const        { return (storage_class & STCfield) != 0; }
     149  
     150      bool isIn()  const  { return (storage_class & STCin) != 0; }
     151      bool isOut() const  { return (storage_class & STCout) != 0; }
     152      bool isRef() const  { return (storage_class & STCref) != 0; }
     153      bool isReference() const { return (storage_class & (STCref | STCout)) != 0; }
     154  
     155      bool isFuture() const { return (storage_class & STCfuture) != 0; }
     156  
     157      Visibility visible() override final;
     158  
     159      Declaration *isDeclaration() override final { return this; }
     160      void accept(Visitor *v) override { v->visit(this); }
     161  };
     162  
     163  /**************************************************************/
     164  
     165  class TupleDeclaration final : public Declaration
     166  {
     167  public:
     168      Objects *objects;
     169      TypeTuple *tupletype;       // !=NULL if this is a type tuple
     170      d_bool isexp;                 // true: expression tuple
     171      d_bool building;              // it's growing in AliasAssign semantic
     172  
     173      TupleDeclaration *syntaxCopy(Dsymbol *) override;
     174      const char *kind() const override;
     175      Type *getType() override;
     176      Dsymbol *toAlias2() override;
     177      bool needThis() override;
     178  
     179      TupleDeclaration *isTupleDeclaration() override { return this; }
     180      void accept(Visitor *v) override { v->visit(this); }
     181  };
     182  
     183  /**************************************************************/
     184  
     185  class AliasDeclaration final : public Declaration
     186  {
     187  public:
     188      Dsymbol *aliassym;
     189      Dsymbol *overnext;          // next in overload list
     190      Dsymbol *_import;           // !=NULL if unresolved internal alias for selective import
     191  
     192      static AliasDeclaration *create(const Loc &loc, Identifier *id, Type *type);
     193      AliasDeclaration *syntaxCopy(Dsymbol *) override;
     194      bool overloadInsert(Dsymbol *s) override;
     195      const char *kind() const override;
     196      Type *getType() override;
     197      Dsymbol *toAlias() override;
     198      Dsymbol *toAlias2() override;
     199      bool isOverloadable() const override;
     200  
     201      AliasDeclaration *isAliasDeclaration() override { return this; }
     202      void accept(Visitor *v) override { v->visit(this); }
     203  };
     204  
     205  /**************************************************************/
     206  
     207  class OverDeclaration final : public Declaration
     208  {
     209  public:
     210      Dsymbol *overnext;          // next in overload list
     211      Dsymbol *aliassym;
     212  
     213      const char *kind() const override;
     214      bool equals(const RootObject * const o) const override;
     215      bool overloadInsert(Dsymbol *s) override;
     216  
     217      Dsymbol *toAlias() override;
     218      Dsymbol *isUnique();
     219      bool isOverloadable() const override;
     220  
     221      OverDeclaration *isOverDeclaration() override { return this; }
     222      void accept(Visitor *v) override { v->visit(this); }
     223  };
     224  
     225  /**************************************************************/
     226  
     227  class VarDeclaration : public Declaration
     228  {
     229  public:
     230      Initializer *_init;
     231      FuncDeclarations nestedrefs; // referenced by these lexically nested functions
     232      TupleDeclaration *aliasTuple;  // if `this` is really a tuple of declarations
     233      VarDeclaration *lastVar;    // Linked list of variables for goto-skips-init detection
     234      Expression *edtor;          // if !=NULL, does the destruction of the variable
     235      IntRange *range;            // if !NULL, the variable is known to be within the range
     236      VarDeclarations *maybes;    // STCmaybescope variables that are assigned to this STCmaybescope variable
     237  
     238      unsigned endlinnum;         // line number of end of scope that this var lives in
     239      unsigned offset;
     240      unsigned sequenceNumber;     // order the variables are declared
     241      structalign_t alignment;
     242  
     243      // When interpreting, these point to the value (NULL if value not determinable)
     244      // The index of this variable on the CTFE stack, ~0u if not allocated
     245      unsigned ctfeAdrOnStack;
     246  private:
     247      uint16_t bitFields;
     248  public:
     249      int8_t canassign; // // it can be assigned to
     250      uint8_t isdataseg; // private data for isDataseg
     251      bool isargptr() const; // if parameter that _argptr points to
     252      bool isargptr(bool v);
     253      bool ctorinit() const; // it has been initialized in a ctor
     254      bool ctorinit(bool v);
     255      bool iscatchvar() const; // this is the exception object variable in catch() clause
     256      bool iscatchvar(bool v);
     257      bool isowner() const; // this is an Owner, despite it being `scope`
     258      bool isowner(bool v);
     259      bool setInCtorOnly() const; // field can only be set in a constructor, as it is const or immutable
     260      bool setInCtorOnly(bool v);
     261      bool onstack() const; // it is a class that was allocated on the stack
     262      bool onstack(bool v);
     263      bool overlapped() const; // if it is a field and has overlapping
     264      bool overlapped(bool v);
     265      bool overlapUnsafe() const; // if it is an overlapping field and the overlaps are unsafe
     266      bool overlapUnsafe(bool v);
     267      bool maybeScope() const; // allow inferring 'scope' for this variable
     268      bool maybeScope(bool v);
     269      bool doNotInferReturn() const; // do not infer 'return' for this variable
     270      bool doNotInferReturn(bool v);
     271      bool isArgDtorVar() const; // temporary created to handle scope destruction of a function argument
     272      bool isArgDtorVar(bool v);
     273      bool isCmacro() const; // if a C macro turned into a C variable
     274      bool isCmacro(bool v);
     275  #if MARS
     276      bool inClosure() const; // is inserted into a GC allocated closure
     277      bool inClosure(bool v);
     278      bool inAlignSection() const; // is inserted into aligned section on stack
     279      bool inAlignSection(bool v);
     280  #endif
     281      static VarDeclaration *create(const Loc &loc, Type *t, Identifier *id, Initializer *init, StorageClass storage_class = STCundefined);
     282      VarDeclaration *syntaxCopy(Dsymbol *) override;
     283      void setFieldOffset(AggregateDeclaration *ad, FieldState& fieldState, bool isunion) override final;
     284      const char *kind() const override;
     285      AggregateDeclaration *isThis() override final;
     286      bool needThis() override final;
     287      bool isExport() const override final;
     288      bool isImportedSymbol() const override final;
     289      bool isCtorinit() const;
     290      bool isDataseg() override final;
     291      bool isThreadlocal() override final;
     292      bool isCTFE();
     293      bool isOverlappedWith(VarDeclaration *v);
     294      bool hasPointers() override final;
     295      bool canTakeAddressOf();
     296      bool needsScopeDtor();
     297      void checkCtorConstInit() override final;
     298      Dsymbol *toAlias() override final;
     299      // Eliminate need for dynamic_cast
     300      VarDeclaration *isVarDeclaration() override final { return (VarDeclaration *)this; }
     301      void accept(Visitor *v) override { v->visit(this); }
     302  };
     303  
     304  /**************************************************************/
     305  
     306  class BitFieldDeclaration : public VarDeclaration
     307  {
     308  public:
     309      Expression *width;
     310  
     311      unsigned fieldWidth;
     312      unsigned bitOffset;
     313  
     314      BitFieldDeclaration *syntaxCopy(Dsymbol *) override;
     315      BitFieldDeclaration *isBitFieldDeclaration() override final { return this; }
     316      void accept(Visitor *v) override { v->visit(this); }
     317  };
     318  
     319  /**************************************************************/
     320  
     321  // This is a shell around a back end symbol
     322  
     323  class SymbolDeclaration final : public Declaration
     324  {
     325  public:
     326      AggregateDeclaration *dsym;
     327  
     328      // Eliminate need for dynamic_cast
     329      SymbolDeclaration *isSymbolDeclaration() override { return (SymbolDeclaration *)this; }
     330      void accept(Visitor *v) override { v->visit(this); }
     331  };
     332  
     333  class TypeInfoDeclaration : public VarDeclaration
     334  {
     335  public:
     336      Type *tinfo;
     337  
     338      static TypeInfoDeclaration *create(Type *tinfo);
     339      TypeInfoDeclaration *syntaxCopy(Dsymbol *) override final;
     340      const char *toChars() const override final;
     341  
     342      TypeInfoDeclaration *isTypeInfoDeclaration() override final { return this; }
     343      void accept(Visitor *v) override { v->visit(this); }
     344  };
     345  
     346  class TypeInfoStructDeclaration final : public TypeInfoDeclaration
     347  {
     348  public:
     349      static TypeInfoStructDeclaration *create(Type *tinfo);
     350  
     351      void accept(Visitor *v) override { v->visit(this); }
     352  };
     353  
     354  class TypeInfoClassDeclaration final : public TypeInfoDeclaration
     355  {
     356  public:
     357      static TypeInfoClassDeclaration *create(Type *tinfo);
     358  
     359      void accept(Visitor *v) override { v->visit(this); }
     360  };
     361  
     362  class TypeInfoInterfaceDeclaration final : public TypeInfoDeclaration
     363  {
     364  public:
     365      static TypeInfoInterfaceDeclaration *create(Type *tinfo);
     366  
     367      void accept(Visitor *v) override { v->visit(this); }
     368  };
     369  
     370  class TypeInfoPointerDeclaration final : public TypeInfoDeclaration
     371  {
     372  public:
     373      static TypeInfoPointerDeclaration *create(Type *tinfo);
     374  
     375      void accept(Visitor *v) override { v->visit(this); }
     376  };
     377  
     378  class TypeInfoArrayDeclaration final : public TypeInfoDeclaration
     379  {
     380  public:
     381      static TypeInfoArrayDeclaration *create(Type *tinfo);
     382  
     383      void accept(Visitor *v) override { v->visit(this); }
     384  };
     385  
     386  class TypeInfoStaticArrayDeclaration final : public TypeInfoDeclaration
     387  {
     388  public:
     389      static TypeInfoStaticArrayDeclaration *create(Type *tinfo);
     390  
     391      void accept(Visitor *v) override { v->visit(this); }
     392  };
     393  
     394  class TypeInfoAssociativeArrayDeclaration final : public TypeInfoDeclaration
     395  {
     396  public:
     397      static TypeInfoAssociativeArrayDeclaration *create(Type *tinfo);
     398  
     399      void accept(Visitor *v) override { v->visit(this); }
     400  };
     401  
     402  class TypeInfoEnumDeclaration final : public TypeInfoDeclaration
     403  {
     404  public:
     405      static TypeInfoEnumDeclaration *create(Type *tinfo);
     406  
     407      void accept(Visitor *v) override { v->visit(this); }
     408  };
     409  
     410  class TypeInfoFunctionDeclaration final : public TypeInfoDeclaration
     411  {
     412  public:
     413      static TypeInfoFunctionDeclaration *create(Type *tinfo);
     414  
     415      void accept(Visitor *v) override { v->visit(this); }
     416  };
     417  
     418  class TypeInfoDelegateDeclaration final : public TypeInfoDeclaration
     419  {
     420  public:
     421      static TypeInfoDelegateDeclaration *create(Type *tinfo);
     422  
     423      void accept(Visitor *v) override { v->visit(this); }
     424  };
     425  
     426  class TypeInfoTupleDeclaration final : public TypeInfoDeclaration
     427  {
     428  public:
     429      static TypeInfoTupleDeclaration *create(Type *tinfo);
     430  
     431      void accept(Visitor *v) override { v->visit(this); }
     432  };
     433  
     434  class TypeInfoConstDeclaration final : public TypeInfoDeclaration
     435  {
     436  public:
     437      static TypeInfoConstDeclaration *create(Type *tinfo);
     438  
     439      void accept(Visitor *v) override { v->visit(this); }
     440  };
     441  
     442  class TypeInfoInvariantDeclaration final : public TypeInfoDeclaration
     443  {
     444  public:
     445      static TypeInfoInvariantDeclaration *create(Type *tinfo);
     446  
     447      void accept(Visitor *v) override { v->visit(this); }
     448  };
     449  
     450  class TypeInfoSharedDeclaration final : public TypeInfoDeclaration
     451  {
     452  public:
     453      static TypeInfoSharedDeclaration *create(Type *tinfo);
     454  
     455      void accept(Visitor *v) override { v->visit(this); }
     456  };
     457  
     458  class TypeInfoWildDeclaration final : public TypeInfoDeclaration
     459  {
     460  public:
     461      static TypeInfoWildDeclaration *create(Type *tinfo);
     462  
     463      void accept(Visitor *v) override { v->visit(this); }
     464  };
     465  
     466  class TypeInfoVectorDeclaration final : public TypeInfoDeclaration
     467  {
     468  public:
     469      static TypeInfoVectorDeclaration *create(Type *tinfo);
     470  
     471      void accept(Visitor *v) override { v->visit(this); }
     472  };
     473  
     474  /**************************************************************/
     475  
     476  class ThisDeclaration final : public VarDeclaration
     477  {
     478  public:
     479      ThisDeclaration *syntaxCopy(Dsymbol *) override;
     480      ThisDeclaration *isThisDeclaration() override { return this; }
     481      void accept(Visitor *v) override { v->visit(this); }
     482  };
     483  
     484  enum class ILS : unsigned char
     485  {
     486      ILSuninitialized,   // not computed yet
     487      ILSno,              // cannot inline
     488      ILSyes              // can inline
     489  };
     490  
     491  /**************************************************************/
     492  
     493  enum class BUILTIN : unsigned char
     494  {
     495      unknown = 255,   /// not known if this is a builtin
     496      unimp = 0,       /// this is not a builtin
     497      gcc,             /// this is a GCC builtin
     498      llvm,            /// this is an LLVM builtin
     499      sin,
     500      cos,
     501      tan,
     502      sqrt,
     503      fabs,
     504      ldexp,
     505      log,
     506      log2,
     507      log10,
     508      exp,
     509      expm1,
     510      exp2,
     511      round,
     512      floor,
     513      ceil,
     514      trunc,
     515      copysign,
     516      pow,
     517      fmin,
     518      fmax,
     519      fma,
     520      isnan,
     521      isinfinity,
     522      isfinite,
     523      bsf,
     524      bsr,
     525      bswap,
     526      popcnt,
     527      yl2x,
     528      yl2xp1,
     529      toPrecFloat,
     530      toPrecDouble,
     531      toPrecReal
     532  };
     533  
     534  Expression *eval_builtin(const Loc &loc, FuncDeclaration *fd, Expressions *arguments);
     535  BUILTIN isBuiltin(FuncDeclaration *fd);
     536  
     537  class FuncDeclaration : public Declaration
     538  {
     539  public:
     540      Statements *frequires;              // in contracts
     541      Ensures *fensures;                  // out contracts
     542      Statement *frequire;                // lowered in contract
     543      Statement *fensure;                 // lowered out contract
     544      Statement *fbody;
     545  
     546      FuncDeclarations foverrides;        // functions this function overrides
     547      FuncDeclaration *fdrequire;         // function that does the in contract
     548      FuncDeclaration *fdensure;          // function that does the out contract
     549  
     550      Expressions *fdrequireParams;       // argument list for __require
     551      Expressions *fdensureParams;        // argument list for __ensure
     552  
     553      const char *mangleString;           // mangled symbol created from mangleExact()
     554  
     555      VarDeclaration *vresult;            // result variable for out contracts
     556      LabelDsymbol *returnLabel;          // where the return goes
     557  
     558      void *isTypeIsolatedCache;          // An AA on the D side to cache an expensive check result
     559  
     560      // used to prevent symbols in different
     561      // scopes from having the same name
     562      DsymbolTable *localsymtab;
     563      VarDeclaration *vthis;              // 'this' parameter (member and nested)
     564      VarDeclaration *v_arguments;        // '_arguments' parameter
     565  
     566      VarDeclaration *v_argptr;           // '_argptr' variable
     567      VarDeclarations *parameters;        // Array of VarDeclaration's for parameters
     568      DsymbolTable *labtab;               // statement label symbol table
     569      Dsymbol *overnext;                  // next in overload list
     570      FuncDeclaration *overnext0;         // next in overload list (only used during IFTI)
     571      Loc endloc;                         // location of closing curly bracket
     572      int vtblIndex;                      // for member functions, index into vtbl[]
     573  
     574      ILS inlineStatusStmt;
     575      ILS inlineStatusExp;
     576      PINLINE inlining;
     577  
     578      int inlineNest;                     // !=0 if nested inline
     579  
     580      // true if errors in semantic3 this function's frame ptr
     581      ForeachStatement *fes;              // if foreach body, this is the foreach
     582      BaseClass* interfaceVirtual;        // if virtual, but only appears in interface vtbl[]
     583      // if !=NULL, then this is the type
     584      // of the 'introducing' function
     585      // this one is overriding
     586      Type *tintro;
     587      StorageClass storage_class2;        // storage class for template onemember's
     588  
     589      // Things that should really go into Scope
     590  
     591      // 1 if there's a return exp; statement
     592      // 2 if there's a throw statement
     593      // 4 if there's an assert(0)
     594      // 8 if there's inline asm
     595      // 16 if there are multiple return statements
     596      int hasReturnExp;
     597  
     598      VarDeclaration *nrvo_var;           // variable to replace with shidden
     599      Symbol *shidden;                    // hidden pointer passed to function
     600  
     601      ReturnStatements *returns;
     602  
     603      GotoStatements *gotos;              // Gotos with forward references
     604  
     605      // set if this is a known, builtin function we can evaluate at compile time
     606      BUILTIN builtin;
     607  
     608      // set if someone took the address of this function
     609      int tookAddressOf;
     610      d_bool requiresClosure;               // this function needs a closure
     611  
     612      // local variables in this function which are referenced by nested functions
     613      VarDeclarations closureVars;
     614  
     615      /** Outer variables which are referenced by this nested function
     616       * (the inverse of closureVars)
     617       */
     618      VarDeclarations outerVars;
     619  
     620      // Sibling nested functions which called this one
     621      FuncDeclarations siblingCallers;
     622  
     623      FuncDeclarations *inlinedNestedCallees;
     624  
     625      AttributeViolation* safetyViolation;
     626  
     627      // Formerly FUNCFLAGS
     628      uint32_t flags;
     629      bool purityInprocess() const;
     630      bool purityInprocess(bool v);
     631      bool safetyInprocess() const;
     632      bool safetyInprocess(bool v);
     633      bool nothrowInprocess() const;
     634      bool nothrowInprocess(bool v);
     635      bool nogcInprocess() const;
     636      bool nogcInprocess(bool v);
     637      bool returnInprocess() const;
     638      bool returnInprocess(bool v);
     639      bool inlineScanned() const;
     640      bool inlineScanned(bool v);
     641      bool inferScope() const;
     642      bool inferScope(bool v);
     643      bool hasCatches() const;
     644      bool hasCatches(bool v);
     645      bool skipCodegen() const;
     646      bool skipCodegen(bool v);
     647      bool printf() const;
     648      bool printf(bool v);
     649      bool scanf() const;
     650      bool scanf(bool v);
     651      bool noreturn() const;
     652      bool noreturn(bool v);
     653      bool isNRVO() const;
     654      bool isNRVO(bool v);
     655      bool isNaked() const;
     656      bool isNaked(bool v);
     657      bool isGenerated() const;
     658      bool isGenerated(bool v);
     659      bool isIntroducing() const;
     660      bool isIntroducing(bool v);
     661      bool hasSemantic3Errors() const;
     662      bool hasSemantic3Errors(bool v);
     663      bool hasNoEH() const;
     664      bool hasNoEH(bool v);
     665      bool inferRetType() const;
     666      bool inferRetType(bool v);
     667      bool hasDualContext() const;
     668      bool hasDualContext(bool v);
     669      bool hasAlwaysInlines() const;
     670      bool hasAlwaysInlines(bool v);
     671      bool isCrtCtor() const;
     672      bool isCrtCtor(bool v);
     673      bool isCrtDtor() const;
     674      bool isCrtDtor(bool v);
     675  
     676      // Data for a function declaration that is needed for the Objective-C
     677      // integration.
     678      ObjcFuncDeclaration objc;
     679  
     680      static FuncDeclaration *create(const Loc &loc, const Loc &endloc, Identifier *id, StorageClass storage_class, Type *type, bool noreturn = false);
     681      FuncDeclaration *syntaxCopy(Dsymbol *) override;
     682      bool functionSemantic();
     683      bool functionSemantic3();
     684      bool equals(const RootObject * const o) const override final;
     685  
     686      int overrides(FuncDeclaration *fd);
     687      int findVtblIndex(Dsymbols *vtbl, int dim);
     688      BaseClass *overrideInterface();
     689      bool overloadInsert(Dsymbol *s) override;
     690      bool inUnittest();
     691      MATCH leastAsSpecialized(FuncDeclaration *g, Identifiers *names);
     692      LabelDsymbol *searchLabel(Identifier *ident, const Loc &loc);
     693      int getLevel(FuncDeclaration *fd, int intypeof); // lexical nesting level difference
     694      int getLevelAndCheck(const Loc &loc, Scope *sc, FuncDeclaration *fd);
     695      const char *toPrettyChars(bool QualifyTypes = false) override;
     696      const char *toFullSignature();  // for diagnostics, e.g. 'int foo(int x, int y) pure'
     697      bool isMain() const;
     698      bool isCMain() const;
     699      bool isWinMain() const;
     700      bool isDllMain() const;
     701      bool isExport() const override final;
     702      bool isImportedSymbol() const override final;
     703      bool isCodeseg() const override final;
     704      bool isOverloadable() const override final;
     705      bool isAbstract() override final;
     706      PURE isPure();
     707      PURE isPureBypassingInference();
     708      bool isSafe();
     709      bool isSafeBypassingInference();
     710      bool isTrusted();
     711  
     712      bool isNogc();
     713      bool isNogcBypassingInference();
     714  
     715      virtual bool isNested() const;
     716      AggregateDeclaration *isThis() override;
     717      bool needThis() override final;
     718      bool isVirtualMethod();
     719      virtual bool isVirtual() const;
     720      bool isFinalFunc() const;
     721      virtual bool addPreInvariant();
     722      virtual bool addPostInvariant();
     723      const char *kind() const override;
     724      bool isUnique();
     725      bool needsClosure();
     726      bool checkClosure();
     727      bool hasNestedFrameRefs();
     728      ParameterList getParameterList();
     729  
     730      static FuncDeclaration *genCfunc(Parameters *args, Type *treturn, const char *name, StorageClass stc=0);
     731      static FuncDeclaration *genCfunc(Parameters *args, Type *treturn, Identifier *id, StorageClass stc=0);
     732  
     733      bool checkNRVO();
     734  
     735      FuncDeclaration *isFuncDeclaration() override final { return this; }
     736  
     737      virtual FuncDeclaration *toAliasFunc() { return this; }
     738      void accept(Visitor *v) override { v->visit(this); }
     739  };
     740  
     741  class FuncAliasDeclaration final : public FuncDeclaration
     742  {
     743  public:
     744      FuncDeclaration *funcalias;
     745      d_bool hasOverloads;
     746  
     747      FuncAliasDeclaration *isFuncAliasDeclaration() override { return this; }
     748      const char *kind() const override;
     749  
     750      FuncDeclaration *toAliasFunc() override;
     751      void accept(Visitor *v) override { v->visit(this); }
     752  };
     753  
     754  class FuncLiteralDeclaration final : public FuncDeclaration
     755  {
     756  public:
     757      TOK tok;                       // TOKfunction or TOKdelegate
     758      Type *treq;                         // target of return type inference
     759  
     760      // backend
     761      d_bool deferToObj;
     762  
     763      FuncLiteralDeclaration *syntaxCopy(Dsymbol *) override;
     764      bool isNested() const override;
     765      AggregateDeclaration *isThis() override;
     766      bool isVirtual() const override;
     767      bool addPreInvariant() override;
     768      bool addPostInvariant() override;
     769  
     770      void modifyReturns(Scope *sc, Type *tret);
     771  
     772      FuncLiteralDeclaration *isFuncLiteralDeclaration() override { return this; }
     773      const char *kind() const override;
     774      const char *toPrettyChars(bool QualifyTypes = false) override;
     775      void accept(Visitor *v) override { v->visit(this); }
     776  };
     777  
     778  class CtorDeclaration final : public FuncDeclaration
     779  {
     780  public:
     781      d_bool isCpCtor;
     782      CtorDeclaration *syntaxCopy(Dsymbol *) override;
     783      const char *kind() const override;
     784      const char *toChars() const override;
     785      bool isVirtual() const override;
     786      bool addPreInvariant() override;
     787      bool addPostInvariant() override;
     788  
     789      CtorDeclaration *isCtorDeclaration() override { return this; }
     790      void accept(Visitor *v) override { v->visit(this); }
     791  };
     792  
     793  class PostBlitDeclaration final : public FuncDeclaration
     794  {
     795  public:
     796      PostBlitDeclaration *syntaxCopy(Dsymbol *) override;
     797      bool isVirtual() const override;
     798      bool addPreInvariant() override;
     799      bool addPostInvariant() override;
     800      bool overloadInsert(Dsymbol *s) override;
     801  
     802      PostBlitDeclaration *isPostBlitDeclaration() override { return this; }
     803      void accept(Visitor *v) override { v->visit(this); }
     804  };
     805  
     806  class DtorDeclaration final : public FuncDeclaration
     807  {
     808  public:
     809      DtorDeclaration *syntaxCopy(Dsymbol *) override;
     810      const char *kind() const override;
     811      const char *toChars() const override;
     812      bool isVirtual() const override;
     813      bool addPreInvariant() override;
     814      bool addPostInvariant() override;
     815      bool overloadInsert(Dsymbol *s) override;
     816  
     817      DtorDeclaration *isDtorDeclaration() override { return this; }
     818      void accept(Visitor *v) override { v->visit(this); }
     819  };
     820  
     821  class StaticCtorDeclaration : public FuncDeclaration
     822  {
     823  public:
     824      StaticCtorDeclaration *syntaxCopy(Dsymbol *) override;
     825      AggregateDeclaration *isThis() override final;
     826      bool isVirtual() const override final;
     827      bool addPreInvariant() override final;
     828      bool addPostInvariant() override final;
     829      bool hasStaticCtorOrDtor() override final;
     830  
     831      StaticCtorDeclaration *isStaticCtorDeclaration() override final { return this; }
     832      void accept(Visitor *v) override { v->visit(this); }
     833  };
     834  
     835  class SharedStaticCtorDeclaration final : public StaticCtorDeclaration
     836  {
     837  public:
     838      SharedStaticCtorDeclaration *syntaxCopy(Dsymbol *) override;
     839  
     840      SharedStaticCtorDeclaration *isSharedStaticCtorDeclaration() override { return this; }
     841      void accept(Visitor *v) override { v->visit(this); }
     842  };
     843  
     844  class StaticDtorDeclaration : public FuncDeclaration
     845  {
     846  public:
     847      VarDeclaration *vgate;      // 'gate' variable
     848  
     849      StaticDtorDeclaration *syntaxCopy(Dsymbol *) override;
     850      AggregateDeclaration *isThis() override final;
     851      bool isVirtual() const override final;
     852      bool hasStaticCtorOrDtor() override final;
     853      bool addPreInvariant() override final;
     854      bool addPostInvariant() override final;
     855  
     856      StaticDtorDeclaration *isStaticDtorDeclaration() override final { return this; }
     857      void accept(Visitor *v) override { v->visit(this); }
     858  };
     859  
     860  class SharedStaticDtorDeclaration final : public StaticDtorDeclaration
     861  {
     862  public:
     863      SharedStaticDtorDeclaration *syntaxCopy(Dsymbol *) override;
     864  
     865      SharedStaticDtorDeclaration *isSharedStaticDtorDeclaration() override { return this; }
     866      void accept(Visitor *v) override { v->visit(this); }
     867  };
     868  
     869  class InvariantDeclaration final : public FuncDeclaration
     870  {
     871  public:
     872      InvariantDeclaration *syntaxCopy(Dsymbol *) override;
     873      bool isVirtual() const override;
     874      bool addPreInvariant() override;
     875      bool addPostInvariant() override;
     876  
     877      InvariantDeclaration *isInvariantDeclaration() override { return this; }
     878      void accept(Visitor *v) override { v->visit(this); }
     879  };
     880  
     881  class UnitTestDeclaration final : public FuncDeclaration
     882  {
     883  public:
     884      char *codedoc; /** For documented unittest. */
     885  
     886      // toObjFile() these nested functions after this one
     887      FuncDeclarations deferredNested;
     888  
     889      UnitTestDeclaration *syntaxCopy(Dsymbol *) override;
     890      AggregateDeclaration *isThis() override;
     891      bool isVirtual() const override;
     892      bool addPreInvariant() override;
     893      bool addPostInvariant() override;
     894  
     895      UnitTestDeclaration *isUnitTestDeclaration() override { return this; }
     896      void accept(Visitor *v) override { v->visit(this); }
     897  };
     898  
     899  class NewDeclaration final : public FuncDeclaration
     900  {
     901  public:
     902      NewDeclaration *syntaxCopy(Dsymbol *) override;
     903      const char *kind() const override;
     904      bool isVirtual() const override;
     905      bool addPreInvariant() override;
     906      bool addPostInvariant() override;
     907  
     908      NewDeclaration *isNewDeclaration() override { return this; }
     909      void accept(Visitor *v) override { v->visit(this); }
     910  };