]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/d/dmd/aggregate.h
d: Merge upstream dmd 13d67c575.
[thirdparty/gcc.git] / gcc / d / dmd / aggregate.h
CommitLineData
b4c522fa
IB
1
2/* Compiler implementation of the D programming language
8e788ac6 3 * Copyright (C) 1999-2020 by The D Language Foundation, All Rights Reserved
b4c522fa
IB
4 * written by Walter Bright
5 * http://www.digitalmars.com
6 * Distributed under the Boost Software License, Version 1.0.
7 * http://www.boost.org/LICENSE_1_0.txt
8 * https://github.com/dlang/dmd/blob/master/src/dmd/aggregate.h
9 */
10
11#pragma once
12
13#include "root/root.h"
14
15#include "dsymbol.h"
16#include "declaration.h"
17#include "objc.h"
18
19class Identifier;
20class Type;
21class TypeFunction;
22class Expression;
23class FuncDeclaration;
24class CtorDeclaration;
25class DtorDeclaration;
26class InvariantDeclaration;
27class NewDeclaration;
28class DeleteDeclaration;
29class InterfaceDeclaration;
30class TypeInfoClassDeclaration;
31class VarDeclaration;
32
33enum Sizeok
34{
35 SIZEOKnone, // size of aggregate is not yet able to compute
36 SIZEOKfwd, // size of aggregate is ready to compute
37 SIZEOKdone // size of aggregate is set correctly
38};
39
40enum Baseok
41{
42 BASEOKnone, // base classes not computed yet
43 BASEOKin, // in process of resolving base classes
44 BASEOKdone, // all base classes are resolved
45 BASEOKsemanticdone // all base classes semantic done
46};
47
48enum StructPOD
49{
50 ISPODno, // struct is not POD
51 ISPODyes, // struct is POD
52 ISPODfwd // POD not yet computed
53};
54
55enum Abstract
56{
57 ABSfwdref = 0, // whether an abstract class is not yet computed
58 ABSyes, // is abstract class
59 ABSno // is not abstract class
60};
61
62FuncDeclaration *hasIdentityOpAssign(AggregateDeclaration *ad, Scope *sc);
63FuncDeclaration *buildOpAssign(StructDeclaration *sd, Scope *sc);
64bool needOpEquals(StructDeclaration *sd);
65FuncDeclaration *buildOpEquals(StructDeclaration *sd, Scope *sc);
66FuncDeclaration *buildXopEquals(StructDeclaration *sd, Scope *sc);
67FuncDeclaration *buildXopCmp(StructDeclaration *sd, Scope *sc);
68FuncDeclaration *buildXtoHash(StructDeclaration *ad, Scope *sc);
69FuncDeclaration *buildPostBlit(StructDeclaration *sd, Scope *sc);
70FuncDeclaration *buildDtor(AggregateDeclaration *ad, Scope *sc);
71FuncDeclaration *buildInv(AggregateDeclaration *ad, Scope *sc);
72FuncDeclaration *search_toString(StructDeclaration *sd);
73
75f758a7
IB
74struct ClassKind
75{
76 enum Type
77 {
78 /// the class is a d(efault) class
79 d,
80 /// the class is a C++ interface
81 cpp,
82 /// the class is an Objective-C class/interface
83 objc,
84 };
85};
86
b4c522fa
IB
87class AggregateDeclaration : public ScopeDsymbol
88{
89public:
90 Type *type;
91 StorageClass storage_class;
92 Prot protection;
93 unsigned structsize; // size of struct
94 unsigned alignsize; // size of struct for alignment purposes
95 VarDeclarations fields; // VarDeclaration fields
96 Sizeok sizeok; // set when structsize contains valid data
97 Dsymbol *deferred; // any deferred semantic2() or semantic3() symbol
98 bool isdeprecated; // true if deprecated
99
75f758a7
IB
100 ClassKind::Type classKind; // specifies the linkage type
101
b4c522fa
IB
102 /* !=NULL if is nested
103 * pointing to the dsymbol that directly enclosing it.
104 * 1. The function that enclosing it (nested struct and class)
105 * 2. The class that enclosing it (nested class only)
106 * 3. If enclosing aggregate is template, its enclosing dsymbol.
107 * See AggregateDeclaraton::makeNested for the details.
108 */
109 Dsymbol *enclosing;
110 VarDeclaration *vthis; // 'this' parameter if this aggregate is nested
111 // Special member functions
112 FuncDeclarations invs; // Array of invariants
113 FuncDeclaration *inv; // invariant
114 NewDeclaration *aggNew; // allocator
115 DeleteDeclaration *aggDelete; // deallocator
116
117 Dsymbol *ctor; // CtorDeclaration or TemplateDeclaration
118
119 // default constructor - should have no arguments, because
120 // it would be stored in TypeInfo_Class.defaultConstructor
121 CtorDeclaration *defaultCtor;
122
123 Dsymbol *aliasthis; // forward unresolved lookups to aliasthis
124 bool noDefaultCtor; // no default construction
125
126 FuncDeclarations dtors; // Array of destructors
127 FuncDeclaration *dtor; // aggregate destructor
128
129 Expression *getRTInfo; // pointer to GC info generated by object.RTInfo(this)
130
131 AggregateDeclaration(Loc loc, Identifier *id);
132 virtual Scope *newScope(Scope *sc);
133 void setScope(Scope *sc);
134 void semantic2(Scope *sc);
135 void semantic3(Scope *sc);
136 bool determineFields();
137 bool determineSize(Loc loc);
138 virtual void finalizeSize() = 0;
139 d_uns64 size(Loc loc);
140 bool checkOverlappedFields();
141 bool fill(Loc loc, Expressions *elements, bool ctorinit);
142 static void alignmember(structalign_t salign, unsigned size, unsigned *poffset);
143 static unsigned placeField(unsigned *nextoffset,
144 unsigned memsize, unsigned memalignsize, structalign_t memalign,
145 unsigned *paggsize, unsigned *paggalignsize, bool isunion);
146 Type *getType();
147 bool isDeprecated(); // is aggregate deprecated?
148 bool isNested();
149 void makeNested();
150 bool isExport() const;
151 Dsymbol *searchCtor();
152
153 Prot prot();
154
155 // 'this' type
156 Type *handleType() { return type; }
157
158 // Back end
159 Symbol *stag; // tag symbol for debug data
160 Symbol *sinit;
161
162 AggregateDeclaration *isAggregateDeclaration() { return this; }
163 void accept(Visitor *v) { v->visit(this); }
164};
165
166struct StructFlags
167{
168 typedef unsigned Type;
169 enum Enum
170 {
171 none = 0x0,
172 hasPointers = 0x1 // NB: should use noPointers as in ClassFlags
173 };
174};
175
176class StructDeclaration : public AggregateDeclaration
177{
178public:
179 int zeroInit; // !=0 if initialize with 0 fill
180 bool hasIdentityAssign; // true if has identity opAssign
181 bool hasIdentityEquals; // true if has identity opEquals
182 FuncDeclarations postblits; // Array of postblit functions
183 FuncDeclaration *postblit; // aggregate postblit
184
185 FuncDeclaration *xeq; // TypeInfo_Struct.xopEquals
186 FuncDeclaration *xcmp; // TypeInfo_Struct.xopCmp
187 FuncDeclaration *xhash; // TypeInfo_Struct.xtoHash
188 static FuncDeclaration *xerreq; // object.xopEquals
189 static FuncDeclaration *xerrcmp; // object.xopCmp
190
191 structalign_t alignment; // alignment applied outside of the struct
192 StructPOD ispod; // if struct is POD
193
194 // For 64 bit Efl function call/return ABI
195 Type *arg1type;
196 Type *arg2type;
197
198 // Even if struct is defined as non-root symbol, some built-in operations
199 // (e.g. TypeidExp, NewExp, ArrayLiteralExp, etc) request its TypeInfo.
200 // For those, today TypeInfo_Struct is generated in COMDAT.
201 bool requestTypeInfo;
202
203 StructDeclaration(Loc loc, Identifier *id, bool inObject);
204 static StructDeclaration *create(Loc loc, Identifier *id, bool inObject);
205 Dsymbol *syntaxCopy(Dsymbol *s);
206 void semantic(Scope *sc);
207 void semanticTypeInfoMembers();
208 Dsymbol *search(const Loc &loc, Identifier *ident, int flags = SearchLocalsOnly);
f9ab59ff 209 const char *kind() const;
b4c522fa
IB
210 void finalizeSize();
211 bool fit(Loc loc, Scope *sc, Expressions *elements, Type *stype);
212 bool isPOD();
213
214 StructDeclaration *isStructDeclaration() { return this; }
215 void accept(Visitor *v) { v->visit(this); }
216};
217
218class UnionDeclaration : public StructDeclaration
219{
220public:
221 UnionDeclaration(Loc loc, Identifier *id);
222 Dsymbol *syntaxCopy(Dsymbol *s);
f9ab59ff 223 const char *kind() const;
b4c522fa
IB
224
225 UnionDeclaration *isUnionDeclaration() { return this; }
226 void accept(Visitor *v) { v->visit(this); }
227};
228
229struct BaseClass
230{
231 Type *type; // (before semantic processing)
232
233 ClassDeclaration *sym;
234 unsigned offset; // 'this' pointer offset
235 // for interfaces: Array of FuncDeclaration's
236 // making up the vtbl[]
237 FuncDeclarations vtbl;
238
239 DArray<BaseClass> baseInterfaces; // if BaseClass is an interface, these
240 // are a copy of the InterfaceDeclaration::interfaces
241
242 BaseClass();
243 BaseClass(Type *type);
244
245 bool fillVtbl(ClassDeclaration *cd, FuncDeclarations *vtbl, int newinstance);
246 void copyBaseInterfaces(BaseClasses *);
247};
248
249struct ClassFlags
250{
251 typedef unsigned Type;
252 enum Enum
253 {
254 isCOMclass = 0x1,
255 noPointers = 0x2,
256 hasOffTi = 0x4,
257 hasCtor = 0x8,
258 hasGetMembers = 0x10,
259 hasTypeInfo = 0x20,
260 isAbstract = 0x40,
261 isCPPclass = 0x80,
262 hasDtor = 0x100
263 };
264};
265
266class ClassDeclaration : public AggregateDeclaration
267{
268public:
269 static ClassDeclaration *object;
270 static ClassDeclaration *throwable;
271 static ClassDeclaration *exception;
272 static ClassDeclaration *errorException;
273 static ClassDeclaration *cpp_type_info_ptr;
274
275 ClassDeclaration *baseClass; // NULL only if this is Object
276 FuncDeclaration *staticCtor;
277 FuncDeclaration *staticDtor;
278 Dsymbols vtbl; // Array of FuncDeclaration's making up the vtbl[]
279 Dsymbols vtblFinal; // More FuncDeclaration's that aren't in vtbl[]
280
281 BaseClasses *baseclasses; // Array of BaseClass's; first is super,
282 // rest are Interface's
283
284 DArray<BaseClass*> interfaces; // interfaces[interfaces_dim] for this class
285 // (does not include baseClass)
286
287 BaseClasses *vtblInterfaces; // array of base interfaces that have
288 // their own vtbl[]
289
290 TypeInfoClassDeclaration *vclassinfo; // the ClassInfo object for this ClassDeclaration
291 bool com; // true if this is a COM class (meaning it derives from IUnknown)
b4c522fa
IB
292 bool isscope; // true if this is a scope class
293 Abstract isabstract; // 0: fwdref, 1: is abstract class, 2: not abstract
294 int inuse; // to prevent recursive attempts
295 Baseok baseok; // set the progress of base classes resolving
296 Symbol *cpp_type_info_ptr_sym; // cached instance of class Id.cpp_type_info_ptr
297
298 ClassDeclaration(Loc loc, Identifier *id, BaseClasses *baseclasses, Dsymbols *members, bool inObject = false);
299 static ClassDeclaration *create(Loc loc, Identifier *id, BaseClasses *baseclasses, Dsymbols *members, bool inObject);
300 Dsymbol *syntaxCopy(Dsymbol *s);
301 Scope *newScope(Scope *sc);
302 void semantic(Scope *sc);
303 bool isBaseOf2(ClassDeclaration *cd);
304
305 #define OFFSET_RUNTIME 0x76543210
306 #define OFFSET_FWDREF 0x76543211
307 virtual bool isBaseOf(ClassDeclaration *cd, int *poffset);
308
309 bool isBaseInfoComplete();
310 Dsymbol *search(const Loc &loc, Identifier *ident, int flags = SearchLocalsOnly);
311 ClassDeclaration *searchBase(Identifier *ident);
312 void finalizeSize();
98866120 313 bool hasMonitor();
b4c522fa
IB
314 bool isFuncHidden(FuncDeclaration *fd);
315 FuncDeclaration *findFunc(Identifier *ident, TypeFunction *tf);
316 void interfaceSemantic(Scope *sc);
317 bool isCOMclass() const;
318 virtual bool isCOMinterface() const;
319 bool isCPPclass() const;
320 virtual bool isCPPinterface() const;
321 bool isAbstract();
322 virtual int vtblOffset() const;
f9ab59ff 323 const char *kind() const;
b4c522fa
IB
324
325 void addLocalClass(ClassDeclarations *);
326
327 // Back end
328 Symbol *vtblsym;
329
330 ClassDeclaration *isClassDeclaration() { return (ClassDeclaration *)this; }
331 void accept(Visitor *v) { v->visit(this); }
332};
333
334class InterfaceDeclaration : public ClassDeclaration
335{
336public:
337 InterfaceDeclaration(Loc loc, Identifier *id, BaseClasses *baseclasses);
338 Dsymbol *syntaxCopy(Dsymbol *s);
339 Scope *newScope(Scope *sc);
340 void semantic(Scope *sc);
341 bool isBaseOf(ClassDeclaration *cd, int *poffset);
342 bool isBaseOf(BaseClass *bc, int *poffset);
f9ab59ff 343 const char *kind() const;
b4c522fa
IB
344 int vtblOffset() const;
345 bool isCPPinterface() const;
346 bool isCOMinterface() const;
347
348 InterfaceDeclaration *isInterfaceDeclaration() { return this; }
349 void accept(Visitor *v) { v->visit(this); }
350};