
/* Compiler implementation of the D programming language
 * Copyright (C) 1999-2023 by The D Language Foundation, All Rights Reserved
 * written by Walter Bright
 * https://www.digitalmars.com
 * Distributed under the Boost Software License, Version 1.0.
 * https://www.boost.org/LICENSE_1_0.txt
 * https://github.com/dlang/dmd/blob/master/src/dmd/aggregate.h
 */

#pragma once

#include "dsymbol.h"
#include "objc.h"

class AliasThis;
class Identifier;
class Type;
class TypeFunction;
class Expression;
class FuncDeclaration;
class CtorDeclaration;
class DtorDeclaration;
class InterfaceDeclaration;
class TypeInfoClassDeclaration;
class VarDeclaration;

enum class Sizeok : uint8_t
{
    none,         // size of aggregate is not yet able to compute
    fwd,          // size of aggregate is ready to compute
    inProcess,    // in the midst of computing the size
    done          // size of aggregate is set correctly
};

enum class Baseok : uint8_t
{
    none,         // base classes not computed yet
    in,           // in process of resolving base classes
    done,         // all base classes are resolved
    semanticdone  // all base classes semantic done
};

FuncDeclaration *search_toString(StructDeclaration *sd);

enum class ClassKind : uint8_t
{
  /// the aggregate is a d(efault) struct/class/interface
  d,
  /// the aggregate is a C++ struct/class/interface
  cpp,
  /// the aggregate is an Objective-C class/interface
  objc,
  /// the aggregate is a C struct
  c,
};

struct MangleOverride
{
    Dsymbol *agg;
    Identifier *id;
};

class AggregateDeclaration : public ScopeDsymbol
{
public:
    Type *type;
    StorageClass storage_class;
    unsigned structsize;        // size of struct
    unsigned alignsize;         // size of struct for alignment purposes
    VarDeclarations fields;     // VarDeclaration fields
    Dsymbol *deferred;          // any deferred semantic2() or semantic3() symbol

    ClassKind classKind;        // specifies the linkage type
    CPPMANGLE cppmangle;

    // overridden symbol with pragma(mangle, "...")
    MangleOverride *pMangleOverride;
    /* !=NULL if is nested
     * pointing to the dsymbol that directly enclosing it.
     * 1. The function that enclosing it (nested struct and class)
     * 2. The class that enclosing it (nested class only)
     * 3. If enclosing aggregate is template, its enclosing dsymbol.
     * See AggregateDeclaraton::makeNested for the details.
     */
    Dsymbol *enclosing;
    VarDeclaration *vthis;      // 'this' parameter if this aggregate is nested
    VarDeclaration *vthis2;     // 'this' parameter if this aggregate is a template and is nested
    // Special member functions
    FuncDeclarations invs;              // Array of invariants
    FuncDeclaration *inv;               // invariant

    Dsymbol *ctor;                      // CtorDeclaration or TemplateDeclaration

    // default constructor - should have no arguments, because
    // it would be stored in TypeInfo_Class.defaultConstructor
    CtorDeclaration *defaultCtor;

    AliasThis *aliasthis;       // forward unresolved lookups to aliasthis

    DtorDeclarations userDtors; // user-defined destructors (`~this()`) - mixins can yield multiple ones
    DtorDeclaration *aggrDtor;  // aggregate destructor calling userDtors and fieldDtor (and base class aggregate dtor for C++ classes)
    DtorDeclaration *dtor;      // the aggregate destructor exposed as `__xdtor` alias
                                // (same as aggrDtor, except for C++ classes with virtual dtor on Windows)
    DtorDeclaration *tidtor;    // aggregate destructor used in TypeInfo (must have extern(D) ABI)
    DtorDeclaration *fieldDtor; // function destructing (non-inherited) fields

    Expression *getRTInfo;      // pointer to GC info generated by object.RTInfo(this)

    Visibility visibility;
    d_bool noDefaultCtor;         // no default construction
    d_bool disableNew;            // disallow allocations using `new`
    Sizeok sizeok;              // set when structsize contains valid data

    virtual Scope *newScope(Scope *sc);
    void setScope(Scope *sc) override final;
    size_t nonHiddenFields();
    bool determineSize(const Loc &loc);
    virtual void finalizeSize() = 0;
    uinteger_t size(const Loc &loc) override final;
    bool fill(const Loc &loc, Expressions &elements, bool ctorinit);
    Type *getType() override final;
    bool isDeprecated() const override final; // is aggregate deprecated?
    void setDeprecated();
    bool isNested() const;
    bool isExport() const override final;
    Dsymbol *searchCtor();

    Visibility visible() override final;

    // 'this' type
    Type *handleType() { return type; }

    bool hasInvariant();

    // Back end
    void *sinit;

    AggregateDeclaration *isAggregateDeclaration() override final { return this; }
    void accept(Visitor *v) override { v->visit(this); }
};

struct StructFlags
{
    enum Type
    {
        none = 0x0,
        hasPointers = 0x1  // NB: should use noPointers as in ClassFlags
    };
};

class StructDeclaration : public AggregateDeclaration
{
public:
    FuncDeclarations postblits; // Array of postblit functions
    FuncDeclaration *postblit;  // aggregate postblit

    FuncDeclaration *xeq;       // TypeInfo_Struct.xopEquals
    FuncDeclaration *xcmp;      // TypeInfo_Struct.xopCmp
    FuncDeclaration *xhash;     // TypeInfo_Struct.xtoHash
    static FuncDeclaration *xerreq;      // object.xopEquals
    static FuncDeclaration *xerrcmp;     // object.xopCmp

    // ABI-specific type(s) if the struct can be passed in registers
    TypeTuple *argTypes;

    structalign_t alignment;    // alignment applied outside of the struct
    ThreeState ispod;           // if struct is POD
private:
    uint16_t bitFields;
public:
    static StructDeclaration *create(const Loc &loc, Identifier *id, bool inObject);
    StructDeclaration *syntaxCopy(Dsymbol *s) override;
    Dsymbol *search(const Loc &loc, Identifier *ident, int flags = SearchLocalsOnly) override final;
    const char *kind() const override;
    void finalizeSize() override final;
    bool isPOD();
    bool zeroInit() const;          // !=0 if initialize with 0 fill
    bool zeroInit(bool v);
    bool hasIdentityAssign() const; // true if has identity opAssign
    bool hasIdentityAssign(bool v);
    bool hasBlitAssign() const;     // true if opAssign is a blit
    bool hasBlitAssign(bool v);
    bool hasIdentityEquals() const; // true if has identity opEquals
    bool hasIdentityEquals(bool v);
    bool hasNoFields() const;       // has no fields
    bool hasNoFields(bool v);
    bool hasCopyCtor() const;       // copy constructor
    bool hasCopyCtor(bool v);
    // Even if struct is defined as non-root symbol, some built-in operations
    // (e.g. TypeidExp, NewExp, ArrayLiteralExp, etc) request its TypeInfo.
    // For those, today TypeInfo_Struct is generated in COMDAT.
    bool requestTypeInfo() const;
    bool requestTypeInfo(bool v);

    StructDeclaration *isStructDeclaration() override final { return this; }
    void accept(Visitor *v) override { v->visit(this); }

    unsigned numArgTypes() const;
    Type *argType(unsigned index);
    bool hasRegularCtor(bool checkDisabled = false);
};

class UnionDeclaration final : public StructDeclaration
{
public:
    UnionDeclaration *syntaxCopy(Dsymbol *s) override;
    const char *kind() const override;

    UnionDeclaration *isUnionDeclaration() override { return this; }
    void accept(Visitor *v) override { v->visit(this); }
};

struct BaseClass
{
    Type *type;                         // (before semantic processing)

    ClassDeclaration *sym;
    unsigned offset;                    // 'this' pointer offset
    // for interfaces: Array of FuncDeclaration's
    // making up the vtbl[]
    FuncDeclarations vtbl;

    DArray<BaseClass> baseInterfaces;   // if BaseClass is an interface, these
                                        // are a copy of the InterfaceDeclaration::interfaces

    bool fillVtbl(ClassDeclaration *cd, FuncDeclarations *vtbl, int newinstance);
};

struct ClassFlags
{
    enum Type
    {
        none = 0x0,
        isCOMclass = 0x1,
        noPointers = 0x2,
        hasOffTi = 0x4,
        hasCtor = 0x8,
        hasGetMembers = 0x10,
        hasTypeInfo = 0x20,
        isAbstract = 0x40,
        isCPPclass = 0x80,
        hasDtor = 0x100
    };
};

class ClassDeclaration : public AggregateDeclaration
{
public:
    static ClassDeclaration *object;
    static ClassDeclaration *throwable;
    static ClassDeclaration *exception;
    static ClassDeclaration *errorException;
    static ClassDeclaration *cpp_type_info_ptr;

    ClassDeclaration *baseClass;        // NULL only if this is Object
    FuncDeclaration *staticCtor;
    FuncDeclaration *staticDtor;
    Dsymbols vtbl;                      // Array of FuncDeclaration's making up the vtbl[]
    Dsymbols vtblFinal;                 // More FuncDeclaration's that aren't in vtbl[]

    BaseClasses *baseclasses;           // Array of BaseClass's; first is super,
                                        // rest are Interface's

    DArray<BaseClass*> interfaces;      // interfaces[interfaces_dim] for this class
                                        // (does not include baseClass)

    BaseClasses *vtblInterfaces;        // array of base interfaces that have
                                        // their own vtbl[]

    TypeInfoClassDeclaration *vclassinfo;       // the ClassInfo object for this ClassDeclaration
    d_bool com;                           // true if this is a COM class (meaning it derives from IUnknown)
    d_bool stack;                         // true if this is a scope class
    int cppDtorVtblIndex;               // slot reserved for the virtual destructor [extern(C++)]
    d_bool inuse;                         // to prevent recursive attempts

    ThreeState isabstract;              // if abstract class
    Baseok baseok;                      // set the progress of base classes resolving
    ObjcClassDeclaration objc;          // Data for a class declaration that is needed for the Objective-C integration
    Symbol *cpp_type_info_ptr_sym;      // cached instance of class Id.cpp_type_info_ptr

    static ClassDeclaration *create(const Loc &loc, Identifier *id, BaseClasses *baseclasses, Dsymbols *members, bool inObject);
    const char *toPrettyChars(bool QualifyTypes = false) override;
    ClassDeclaration *syntaxCopy(Dsymbol *s) override;
    Scope *newScope(Scope *sc) override;
    bool isBaseOf2(ClassDeclaration *cd);

    #define OFFSET_RUNTIME 0x76543210
    #define OFFSET_FWDREF 0x76543211
    virtual bool isBaseOf(ClassDeclaration *cd, int *poffset);

    bool isBaseInfoComplete();
    Dsymbol *search(const Loc &loc, Identifier *ident, int flags = SearchLocalsOnly) override final;
    ClassDeclaration *searchBase(Identifier *ident);
    void finalizeSize() override;
    bool hasMonitor();
    bool isFuncHidden(FuncDeclaration *fd);
    FuncDeclaration *findFunc(Identifier *ident, TypeFunction *tf);
    bool isCOMclass() const;
    virtual bool isCOMinterface() const;
    bool isCPPclass() const;
    virtual bool isCPPinterface() const;
    bool isAbstract();
    virtual int vtblOffset() const;
    const char *kind() const override;

    void addObjcSymbols(ClassDeclarations *classes, ClassDeclarations *categories) override final;

    // Back end
    Dsymbol *vtblsym;
    Dsymbol *vtblSymbol();

    ClassDeclaration *isClassDeclaration() override final { return (ClassDeclaration *)this; }
    void accept(Visitor *v) override { v->visit(this); }
};

class InterfaceDeclaration final : public ClassDeclaration
{
public:
    InterfaceDeclaration *syntaxCopy(Dsymbol *s) override;
    Scope *newScope(Scope *sc) override;
    bool isBaseOf(ClassDeclaration *cd, int *poffset) override;
    const char *kind() const override;
    int vtblOffset() const override;
    bool isCPPinterface() const override;
    bool isCOMinterface() const override;

    InterfaceDeclaration *isInterfaceDeclaration() override { return this; }
    void accept(Visitor *v) override { v->visit(this); }
};
