]>
git.ipfire.org Git - thirdparty/gcc.git/blob - gcc/d/dmd/dstruct.c
2 /* Compiler implementation of the D programming language
3 * Copyright (C) 1999-2018 by The D Language Foundation, All Rights Reserved
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/D-Programming-Language/dmd/blob/master/src/struct.c
11 #include "root/dsystem.h"
12 #include "root/root.h"
15 #include "aggregate.h"
19 #include "declaration.h"
22 #include "statement.h"
26 Type
*getTypeInfoType(Type
*t
, Scope
*sc
);
27 TypeTuple
*toArgTypes(Type
*t
);
28 void unSpeculative(Scope
*sc
, RootObject
*o
);
29 bool MODimplicitConv(MOD modfrom
, MOD modto
);
30 Expression
*resolve(Loc loc
, Scope
*sc
, Dsymbol
*s
, bool hasOverloads
);
32 FuncDeclaration
*StructDeclaration::xerreq
; // object.xopEquals
33 FuncDeclaration
*StructDeclaration::xerrcmp
; // object.xopCmp
35 /***************************************
36 * Search toString member function for TypeInfo_Struct.
39 FuncDeclaration
*search_toString(StructDeclaration
*sd
)
41 Dsymbol
*s
= search_function(sd
, Id::tostring
);
42 FuncDeclaration
*fd
= s
? s
->isFuncDeclaration() : NULL
;
45 static TypeFunction
*tftostring
;
48 tftostring
= new TypeFunction(NULL
, Type::tstring
, 0, LINKd
);
49 tftostring
= (TypeFunction
*)tftostring
->merge();
52 fd
= fd
->overloadExactMatch(tftostring
);
57 /***************************************
58 * Request additonal semantic analysis for TypeInfo generation.
60 void semanticTypeInfo(Scope
*sc
, Type
*t
)
62 class FullTypeInfoVisitor
: public Visitor
69 Type
*tb
= t
->toBasetype();
73 void visit(TypeNext
*t
)
76 t
->next
->accept(this);
78 void visit(TypeBasic
*) { }
79 void visit(TypeVector
*t
)
81 t
->basetype
->accept(this);
83 void visit(TypeAArray
*t
)
85 t
->index
->accept(this);
88 void visit(TypeFunction
*t
)
91 // Currently TypeInfo_Function doesn't store parameter types.
93 void visit(TypeStruct
*t
)
95 StructDeclaration
*sd
= t
->sym
;
97 /* Step 1: create TypeInfoDeclaration
99 if (!sc
) // inline may request TypeInfo.
102 scx
._module
= sd
->getModule();
103 getTypeInfoType(t
, &scx
);
104 sd
->requestTypeInfo
= true;
108 // don't yet have to generate TypeInfo instance if
109 // the typeid(T) expression exists in speculative scope.
113 getTypeInfoType(t
, sc
);
114 sd
->requestTypeInfo
= true;
116 // Bugzilla 15149, if the typeid operand type comes from a
117 // result of auto function, it may be yet speculative.
118 unSpeculative(sc
, sd
);
121 /* Step 2: If the TypeInfo generation requires sd.semantic3, run it later.
122 * This should be done even if typeid(T) exists in speculative scope.
123 * Because it may appear later in non-speculative scope.
126 return; // opaque struct
127 if (!sd
->xeq
&& !sd
->xcmp
&& !sd
->postblit
&&
128 !sd
->dtor
&& !sd
->xhash
&& !search_toString(sd
))
129 return; // none of TypeInfo-specific members
131 // If the struct is in a non-root module, run semantic3 to get
132 // correct symbols for the member function.
133 if (sd
->semanticRun
>= PASSsemantic3
)
135 // semantic3 is already done
137 else if (TemplateInstance
*ti
= sd
->isInstantiated())
139 if (ti
->minst
&& !ti
->minst
->isRoot())
140 Module::addDeferredSemantic3(sd
);
146 //printf("deferred sem3 for TypeInfo - sd = %s, inNonRoot = %d\n", sd->toChars(), sd->inNonRoot());
147 Module::addDeferredSemantic3(sd
);
151 void visit(TypeClass
*) { }
152 void visit(TypeTuple
*t
)
156 for (size_t i
= 0; i
< t
->arguments
->dim
; i
++)
158 Type
*tprm
= (*t
->arguments
)[i
]->type
;
172 if (sc
->flags
& (SCOPEctfe
| SCOPEcompile
))
176 FullTypeInfoVisitor v
;
181 /********************************* AggregateDeclaration ****************************/
183 AggregateDeclaration::AggregateDeclaration(Loc loc
, Identifier
*id
)
189 protection
= Prot(PROTpublic
);
191 structsize
= 0; // size of struct
192 alignsize
= 0; // size of struct for alignment purposes
193 sizeok
= SIZEOKnone
; // size not determined yet
195 isdeprecated
= false;
208 noDefaultCtor
= false;
213 Prot
AggregateDeclaration::prot()
218 /***************************************
219 * Create a new scope from sc.
220 * semantic, semantic2 and semantic3 will use this for aggregate members.
222 Scope
*AggregateDeclaration::newScope(Scope
*sc
)
224 Scope
*sc2
= sc
->push(this);
225 sc2
->stc
&= STCsafe
| STCtrusted
| STCsystem
;
227 if (isUnionDeclaration())
229 sc2
->protection
= Prot(PROTpublic
);
230 sc2
->explicitProtection
= 0;
231 sc2
->aligndecl
= NULL
;
232 sc2
->userAttribDecl
= NULL
;
236 void AggregateDeclaration::setScope(Scope
*sc
)
238 // Might need a scope to resolve forward references. The check for
239 // semanticRun prevents unnecessary setting of _scope during deferred
240 // setScope phases for aggregates which already finished semantic().
241 // Also see https://issues.dlang.org/show_bug.cgi?id=16607
242 if (semanticRun
< PASSsemanticdone
)
243 ScopeDsymbol::setScope(sc
);
246 void AggregateDeclaration::semantic2(Scope
*sc
)
248 //printf("AggregateDeclaration::semantic2(%s) type = %s, errors = %d\n", toChars(), type->toChars(), errors);
254 error("has forward references");
258 Scope
*sc2
= newScope(sc
);
262 for (size_t i
= 0; i
< members
->dim
; i
++)
264 Dsymbol
*s
= (*members
)[i
];
265 //printf("\t[%d] %s\n", i, s->toChars());
272 void AggregateDeclaration::semantic3(Scope
*sc
)
274 //printf("AggregateDeclaration::semantic3(%s) type = %s, errors = %d\n", toChars(), type->toChars(), errors);
278 StructDeclaration
*sd
= isStructDeclaration();
279 if (!sc
) // from runDeferredSemantic3 for TypeInfo generation
282 sd
->semanticTypeInfoMembers();
286 Scope
*sc2
= newScope(sc
);
288 for (size_t i
= 0; i
< members
->dim
; i
++)
290 Dsymbol
*s
= (*members
)[i
];
296 // don't do it for unused deprecated types
298 if (!getRTInfo
&& Type::rtinfo
&&
299 (!isDeprecated() || global
.params
.useDeprecated
!= DIAGNOSTICerror
) &&
300 (type
&& type
->ty
!= Terror
))
302 // Evaluate: RTinfo!type
303 Objects
*tiargs
= new Objects();
305 TemplateInstance
*ti
= new TemplateInstance(loc
, Type::rtinfo
, tiargs
);
307 Scope
*sc3
= ti
->tempdecl
->_scope
->startCTFE();
308 sc3
->tinst
= sc
->tinst
;
309 sc3
->minst
= sc
->minst
;
311 sc3
->stc
|= STCdeprecated
;
316 Expression
*e
= resolve(Loc(), sc3
, ti
->toAlias(), false);
320 e
= e
->ctfeInterpret();
325 sd
->semanticTypeInfoMembers();
328 /***************************************
329 * Find all instance fields, then push them into `fields`.
331 * Runs semantic() for all instance field variables, but also
332 * the field types can reamin yet not resolved forward references,
333 * except direct recursive definitions.
334 * After the process sizeok is set to SIZEOKfwd.
337 * false if any errors occur.
339 bool AggregateDeclaration::determineFields()
341 if (sizeok
!= SIZEOKnone
)
344 //printf("determineFields() %s, fields.dim = %d\n", toChars(), fields.dim);
349 AggregateDeclaration
*agg
;
351 static int func(Dsymbol
*s
, void *param
)
353 VarDeclaration
*v
= s
->isVarDeclaration();
356 if (v
->storage_class
& STCmanifest
)
359 AggregateDeclaration
*ad
= ((SV
*)param
)->agg
;
363 // Note: Aggregate fields or size could have determined during v->semantic.
364 if (ad
->sizeok
!= SIZEOKnone
)
368 return 0; // If this variable was really a tuple, skip it.
370 if (v
->storage_class
& (STCstatic
| STCextern
| STCtls
| STCgshared
| STCmanifest
| STCctfe
| STCtemplateparameter
))
372 if (!v
->isField() || v
->semanticRun
< PASSsemanticdone
)
373 return 1; // unresolvable forward reference
377 if (v
->storage_class
& STCref
)
379 Type
*tv
= v
->type
->baseElemOf();
380 if (tv
->ty
!= Tstruct
)
382 if (ad
== ((TypeStruct
*)tv
)->sym
)
384 const char *psz
= (v
->type
->toBasetype()->ty
== Tsarray
) ? "static array of " : "";
385 ad
->error("cannot have field %s with %ssame struct type", v
->toChars(), psz
);
386 ad
->type
= Type::terror
;
396 for (size_t i
= 0; i
< members
->dim
; i
++)
398 Dsymbol
*s
= (*members
)[i
];
399 if (s
->apply(&SV::func
, &sv
))
401 if (sizeok
!= SIZEOKnone
)
407 if (sizeok
!= SIZEOKdone
)
413 /***************************************
414 * Collect all instance fields, then determine instance size.
416 * false if failed to determine the size.
418 bool AggregateDeclaration::determineSize(Loc loc
)
420 //printf("AggregateDeclaration::determineSize() %s, sizeok = %d\n", toChars(), sizeok);
422 // The previous instance size finalizing had:
423 if (type
->ty
== Terror
)
424 return false; // failed already
425 if (sizeok
== SIZEOKdone
)
426 return true; // succeeded
430 error(loc
, "unknown size");
437 // Determine the instance size of base class first.
438 if (ClassDeclaration
*cd
= isClassDeclaration())
441 if (cd
&& !cd
->determineSize(loc
))
445 // Determine instance fields when sizeok == SIZEOKnone
446 if (!determineFields())
448 if (sizeok
!= SIZEOKdone
)
451 // this aggregate type has:
452 if (type
->ty
== Terror
)
453 return false; // marked as invalid during the finalizing.
454 if (sizeok
== SIZEOKdone
)
455 return true; // succeeded to calculate instance size.
458 // There's unresolvable forward reference.
459 if (type
!= Type::terror
)
460 error(loc
, "no size because of forward reference");
461 // Don't cache errors from speculative semantic, might be resolvable later.
462 // https://issues.dlang.org/show_bug.cgi?id=16574
471 void StructDeclaration::semanticTypeInfoMembers()
475 xeq
->semanticRun
< PASSsemantic3done
)
477 unsigned errors
= global
.startGagging();
478 xeq
->semantic3(xeq
->_scope
);
479 if (global
.endGagging(errors
))
485 xcmp
->semanticRun
< PASSsemantic3done
)
487 unsigned errors
= global
.startGagging();
488 xcmp
->semantic3(xcmp
->_scope
);
489 if (global
.endGagging(errors
))
493 FuncDeclaration
*ftostr
= search_toString(this);
496 ftostr
->semanticRun
< PASSsemantic3done
)
498 ftostr
->semantic3(ftostr
->_scope
);
503 xhash
->semanticRun
< PASSsemantic3done
)
505 xhash
->semantic3(xhash
->_scope
);
510 postblit
->semanticRun
< PASSsemantic3done
)
512 postblit
->semantic3(postblit
->_scope
);
517 dtor
->semanticRun
< PASSsemantic3done
)
519 dtor
->semantic3(dtor
->_scope
);
523 d_uns64
AggregateDeclaration::size(Loc loc
)
525 //printf("+AggregateDeclaration::size() %s, scope = %p, sizeok = %d\n", toChars(), _scope, sizeok);
526 bool ok
= determineSize(loc
);
527 //printf("-AggregateDeclaration::size() %s, scope = %p, sizeok = %d\n", toChars(), _scope, sizeok);
528 return ok
? structsize
: SIZE_INVALID
;
531 Type
*AggregateDeclaration::getType()
536 bool AggregateDeclaration::isDeprecated()
541 bool AggregateDeclaration::isExport() const
543 return protection
.kind
== PROTexport
;
546 /***************************************
547 * Calculate field[i].overlapped and overlapUnsafe, and check that all of explicit
548 * field initializers have unique memory space on instance.
550 * true if any errors happen.
553 bool AggregateDeclaration::checkOverlappedFields()
555 //printf("AggregateDeclaration::checkOverlappedFields() %s\n", toChars());
556 assert(sizeok
== SIZEOKdone
);
557 size_t nfields
= fields
.dim
;
560 ClassDeclaration
*cd
= isClassDeclaration();
561 if (!cd
|| !cd
->baseClass
|| !cd
->baseClass
->isNested())
566 // Fill in missing any elements with default initializers
567 for (size_t i
= 0; i
< nfields
; i
++)
569 VarDeclaration
*vd
= fields
[i
];
576 VarDeclaration
*vx
= vd
;
577 if (vd
->_init
&& vd
->_init
->isVoidInitializer())
580 // Find overlapped fields with the hole [vd->offset .. vd->offset->size()].
581 for (size_t j
= 0; j
< nfields
; j
++)
585 VarDeclaration
*v2
= fields
[j
];
591 if (!vd
->isOverlappedWith(v2
))
594 // vd and v2 are overlapping.
595 vd
->overlapped
= true;
596 v2
->overlapped
= true;
598 if (!MODimplicitConv(vd
->type
->mod
, v2
->type
->mod
))
599 v2
->overlapUnsafe
= true;
600 if (!MODimplicitConv(v2
->type
->mod
, vd
->type
->mod
))
601 vd
->overlapUnsafe
= true;
605 if (v2
->_init
&& v2
->_init
->isVoidInitializer())
608 if (vx
->_init
&& v2
->_init
)
610 ::error(loc
, "overlapping default initialization for field %s and %s", v2
->toChars(), vd
->toChars());
618 /***************************************
619 * Fill out remainder of elements[] with default initializers for fields[].
622 * elements: explicit arguments which given to construct object.
623 * ctorinit: true if the elements will be used for default initialization.
625 * false if any errors occur.
626 * Otherwise, returns true and the missing arguments will be pushed in elements[].
628 bool AggregateDeclaration::fill(Loc loc
, Expressions
*elements
, bool ctorinit
)
630 //printf("AggregateDeclaration::fill() %s\n", toChars());
631 assert(sizeok
== SIZEOKdone
);
633 size_t nfields
= fields
.dim
- isNested();
636 size_t dim
= elements
->dim
;
637 elements
->setDim(nfields
);
638 for (size_t i
= dim
; i
< nfields
; i
++)
639 (*elements
)[i
] = NULL
;
641 // Fill in missing any elements with default initializers
642 for (size_t i
= 0; i
< nfields
; i
++)
647 VarDeclaration
*vd
= fields
[i
];
648 VarDeclaration
*vx
= vd
;
649 if (vd
->_init
&& vd
->_init
->isVoidInitializer())
652 // Find overlapped fields with the hole [vd->offset .. vd->offset->size()].
654 for (size_t j
= 0; j
< nfields
; j
++)
658 VarDeclaration
*v2
= fields
[j
];
659 if (!vd
->isOverlappedWith(v2
))
667 if (v2
->_init
&& v2
->_init
->isVoidInitializer())
672 /* Prefer first found non-void-initialized field
673 * union U { int a; int b = 2; }
674 * U u; // Error: overlapping initialization for field a and b
683 ::error(loc
, "overlapping initialization for field %s and %s",
684 v2
->toChars(), vd
->toChars());
690 // Will fix Bugzilla 1432 by enabling this path always
692 /* Prefer explicitly initialized field
693 * union U { int a; int b = 2; }
694 * U u; // OK (u.b == 2)
696 if (!vx
|| (!vx
->_init
&& v2
->_init
))
701 else if (vx
!= vd
&& !vx
->isOverlappedWith(v2
))
703 // Both vx and v2 fills vd, but vx and v2 does not overlap
705 else if (vx
->_init
&& v2
->_init
)
707 ::error(loc
, "overlapping default initialization for field %s and %s",
708 v2
->toChars(), vd
->toChars());
712 assert(vx
->_init
|| (!vx
->_init
&& !v2
->_init
));
718 if (vx
->type
->size() == 0)
724 assert(!vx
->_init
->isVoidInitializer());
725 e
= vx
->getConstInitializer(false);
729 if ((vx
->storage_class
& STCnodefaultctor
) && !ctorinit
)
731 ::error(loc
, "field %s.%s must be initialized because it has no default constructor",
732 type
->toChars(), vx
->toChars());
736 /* Bugzilla 12509: Get the element of static array type.
738 Type
*telem
= vx
->type
;
739 if (telem
->ty
== Tsarray
)
741 /* We cannot use Type::baseElemOf() here.
742 * If the bottom of the Tsarray is an enum type, baseElemOf()
743 * will return the base of the enum, and its default initializer
744 * would be different from the enum's.
746 while (telem
->toBasetype()->ty
== Tsarray
)
747 telem
= ((TypeSArray
*)telem
->toBasetype())->next
;
749 if (telem
->ty
== Tvoid
)
750 telem
= Type::tuns8
->addMod(telem
->mod
);
752 if (telem
->needsNested() && ctorinit
)
753 e
= telem
->defaultInit(loc
);
755 e
= telem
->defaultInitLiteral(loc
);
757 (*elements
)[fieldi
] = e
;
761 for (size_t i
= 0; i
< elements
->dim
; i
++)
763 Expression
*e
= (*elements
)[i
];
764 if (e
&& e
->op
== TOKerror
)
771 /****************************
772 * Do byte or word alignment as necessary.
773 * Align sizes of 0, as we may not know array sizes yet.
775 * alignment: struct alignment that is in effect
776 * size: alignment requirement of field
779 void AggregateDeclaration::alignmember(
780 structalign_t alignment
,
784 //printf("alignment = %d, size = %d, offset = %d\n",alignment,size,offset);
787 case (structalign_t
) 1:
791 case (structalign_t
) STRUCTALIGN_DEFAULT
:
792 // Alignment in Target::fieldalignsize must match what the
793 // corresponding C compiler's default alignment behavior is.
794 assert(size
> 0 && !(size
& (size
- 1)));
795 *poffset
= (*poffset
+ size
- 1) & ~(size
- 1);
799 // Align on alignment boundary, which must be a positive power of 2
800 assert(alignment
> 0 && !(alignment
& (alignment
- 1)));
801 *poffset
= (*poffset
+ alignment
- 1) & ~(alignment
- 1);
806 /****************************************
807 * Place a member (mem) into an aggregate (agg), which can be a struct, union or class
809 * offset to place field at
811 * nextoffset: next location in aggregate
812 * memsize: size of member
813 * memalignsize: natural alignment of member
814 * alignment: alignment in effect for this member
815 * paggsize: size of aggregate (updated)
816 * paggalignsize: alignment of aggregate (updated)
817 * isunion: the aggregate is a union
819 unsigned AggregateDeclaration::placeField(
820 unsigned *nextoffset
,
822 unsigned memalignsize
,
823 structalign_t alignment
,
825 unsigned *paggalignsize
,
829 unsigned ofs
= *nextoffset
;
831 const unsigned actualAlignment
=
832 alignment
== STRUCTALIGN_DEFAULT
? memalignsize
: alignment
;
834 alignmember(alignment
, memalignsize
, &ofs
);
835 unsigned memoffset
= ofs
;
842 if (*paggalignsize
< actualAlignment
)
843 *paggalignsize
= actualAlignment
;
849 /****************************************
850 * Returns true if there's an extra member which is the 'this'
851 * pointer to the enclosing context (enclosing aggregate or function)
854 bool AggregateDeclaration::isNested()
856 return enclosing
!= NULL
;
859 /* Append vthis field (this->tupleof[$-1]) to make this aggregate type nested.
861 void AggregateDeclaration::makeNested()
863 if (enclosing
) // if already nested
865 if (sizeok
== SIZEOKdone
)
867 if (isUnionDeclaration() || isInterfaceDeclaration())
869 if (storage_class
& STCstatic
)
872 // If nested struct, add in hidden 'this' pointer to outer scope
873 Dsymbol
*s
= toParent2();
877 if (FuncDeclaration
*fd
= s
->isFuncDeclaration())
881 /* Bugzilla 14422: If a nested class parent is a function, its
882 * context pointer (== `outer`) should be void* always.
886 else if (AggregateDeclaration
*ad
= s
->isAggregateDeclaration())
888 if (isClassDeclaration() && ad
->isClassDeclaration())
892 else if (isStructDeclaration())
894 if (TemplateInstance
*ti
= ad
->parent
->isTemplateInstance())
896 enclosing
= ti
->enclosing
;
900 t
= ad
->handleType();
904 //printf("makeNested %s, enclosing = %s\n", toChars(), enclosing->toChars());
906 if (t
->ty
== Tstruct
)
907 t
= Type::tvoidptr
; // t should not be a ref type
909 vthis
= new ThisDeclaration(loc
, t
);
910 //vthis->storage_class |= STCref;
912 // Emulate vthis->addMember()
913 members
->push(vthis
);
915 // Emulate vthis->semantic()
916 vthis
->storage_class
|= STCfield
;
917 vthis
->parent
= this;
918 vthis
->protection
= Prot(PROTpublic
);
919 vthis
->alignment
= t
->alignment();
920 vthis
->semanticRun
= PASSsemanticdone
;
922 if (sizeok
== SIZEOKfwd
)
927 /*******************************************
928 * Look for constructor declaration.
930 Dsymbol
*AggregateDeclaration::searchCtor()
932 Dsymbol
*s
= search(Loc(), Id::ctor
);
935 if (!(s
->isCtorDeclaration() ||
936 s
->isTemplateDeclaration() ||
939 s
->error("is not a constructor; identifiers starting with __ are reserved for the implementation");
944 if (s
&& s
->toParent() != this)
945 s
= NULL
; // search() looks through ancestor classes
948 // Finish all constructors semantics to determine this->noDefaultCtor.
951 static int fp(Dsymbol
*s
, void *)
953 CtorDeclaration
*f
= s
->isCtorDeclaration();
954 if (f
&& f
->semanticRun
== PASSinit
)
960 for (size_t i
= 0; i
< members
->dim
; i
++)
962 Dsymbol
*sm
= (*members
)[i
];
963 sm
->apply(&SearchCtor::fp
, NULL
);
969 /********************************* StructDeclaration ****************************/
971 StructDeclaration::StructDeclaration(Loc loc
, Identifier
*id
, bool inObject
)
972 : AggregateDeclaration(loc
, id
)
974 zeroInit
= 0; // assume false until we do semantic processing
975 hasIdentityAssign
= false;
976 hasIdentityEquals
= false;
986 requestTypeInfo
= false;
988 // For forward references
989 type
= new TypeStruct(this);
993 if (id
== Id::ModuleInfo
&& !Module::moduleinfo
)
994 Module::moduleinfo
= this;
998 StructDeclaration
*StructDeclaration::create(Loc loc
, Identifier
*id
, bool inObject
)
1000 return new StructDeclaration(loc
, id
, inObject
);
1003 Dsymbol
*StructDeclaration::syntaxCopy(Dsymbol
*s
)
1005 StructDeclaration
*sd
=
1006 s
? (StructDeclaration
*)s
1007 : new StructDeclaration(loc
, ident
, false);
1008 return ScopeDsymbol::syntaxCopy(sd
);
1011 void StructDeclaration::semantic(Scope
*sc
)
1013 //printf("StructDeclaration::semantic(this=%p, %s '%s', sizeok = %d)\n", this, parent->toChars(), toChars(), sizeok);
1015 //static int count; if (++count == 20) halt();
1017 if (semanticRun
>= PASSsemanticdone
)
1019 unsigned errors
= global
.errors
;
1021 //printf("+StructDeclaration::semantic(this=%p, %s '%s', sizeok = %d)\n", this, parent->toChars(), toChars(), sizeok);
1026 scx
= _scope
; // save so we don't make redundant copies
1032 assert(sc
->parent
&& sc
->func
);
1033 parent
= sc
->parent
;
1035 assert(parent
&& !isAnonymous());
1038 type
= Type::terror
;
1039 if (semanticRun
== PASSinit
)
1040 type
= type
->addSTC(sc
->stc
| storage_class
);
1041 type
= type
->semantic(loc
, sc
);
1043 if (type
->ty
== Tstruct
&& ((TypeStruct
*)type
)->sym
!= this)
1045 TemplateInstance
*ti
= ((TypeStruct
*)type
)->sym
->isInstantiated();
1046 if (ti
&& isError(ti
))
1047 ((TypeStruct
*)type
)->sym
= this;
1050 // Ungag errors when not speculative
1051 Ungag ungag
= ungagSpeculative();
1053 if (semanticRun
== PASSinit
)
1055 protection
= sc
->protection
;
1057 alignment
= sc
->alignment();
1059 storage_class
|= sc
->stc
;
1060 if (storage_class
& STCdeprecated
)
1061 isdeprecated
= true;
1062 if (storage_class
& STCabstract
)
1063 error("structs, unions cannot be abstract");
1064 userAttribDecl
= sc
->userAttribDecl
;
1066 else if (symtab
&& !scx
)
1070 semanticRun
= PASSsemantic
;
1072 if (!members
) // if opaque declaration
1074 semanticRun
= PASSsemanticdone
;
1079 symtab
= new DsymbolTable();
1081 for (size_t i
= 0; i
< members
->dim
; i
++)
1083 Dsymbol
*s
= (*members
)[i
];
1084 //printf("adding member '%s' to '%s'\n", s->toChars(), this->toChars());
1085 s
->addMember(sc
, this);
1089 Scope
*sc2
= newScope(sc
);
1091 /* Set scope so if there are forward references, we still might be able to
1092 * resolve individual members like enums.
1094 for (size_t i
= 0; i
< members
->dim
; i
++)
1096 Dsymbol
*s
= (*members
)[i
];
1097 //printf("struct: setScope %s %s\n", s->kind(), s->toChars());
1101 for (size_t i
= 0; i
< members
->dim
; i
++)
1103 Dsymbol
*s
= (*members
)[i
];
1107 for (size_t i
= 0; i
< members
->dim
; i
++)
1109 Dsymbol
*s
= (*members
)[i
];
1113 if (!determineFields())
1115 assert(type
->ty
== Terror
);
1117 semanticRun
= PASSsemanticdone
;
1121 /* Following special member functions creation needs semantic analysis
1122 * completion of sub-structs in each field types. For example, buildDtor
1123 * needs to check existence of elaborate dtor in type of each fields.
1124 * See the case in compilable/test14838.d
1126 for (size_t i
= 0; i
< fields
.dim
; i
++)
1128 VarDeclaration
*v
= fields
[i
];
1129 Type
*tb
= v
->type
->baseElemOf();
1130 if (tb
->ty
!= Tstruct
)
1132 StructDeclaration
*sd
= ((TypeStruct
*)tb
)->sym
;
1133 if (sd
->semanticRun
>= PASSsemanticdone
)
1138 _scope
= scx
? scx
: sc
->copy();
1139 _scope
->setNoFree();
1140 _scope
->_module
->addDeferredSemantic(this);
1142 //printf("\tdeferring %s\n", toChars());
1146 /* Look for special member functions.
1148 aggNew
= (NewDeclaration
*)search(Loc(), Id::classNew
);
1149 aggDelete
= (DeleteDeclaration
*)search(Loc(), Id::classDelete
);
1151 // Look for the constructor
1152 ctor
= searchCtor();
1154 dtor
= buildDtor(this, sc2
);
1155 postblit
= buildPostBlit(this, sc2
);
1157 buildOpAssign(this, sc2
);
1158 buildOpEquals(this, sc2
);
1160 xeq
= buildXopEquals(this, sc2
);
1161 xcmp
= buildXopCmp(this, sc2
);
1162 xhash
= buildXtoHash(this, sc2
);
1164 inv
= buildInv(this, sc2
);
1166 Module::dprogress
++;
1167 semanticRun
= PASSsemanticdone
;
1168 //printf("-StructDeclaration::semantic(this=%p, '%s')\n", this, toChars());
1174 Dsymbol
*scall
= search(Loc(), Id::call
);
1177 unsigned xerrors
= global
.startGagging();
1181 FuncDeclaration
*fcall
= resolveFuncCall(loc
, sc
, scall
, NULL
, NULL
, NULL
, 1);
1183 global
.endGagging(xerrors
);
1185 if (fcall
&& fcall
->isStatic())
1187 error(fcall
->loc
, "static opCall is hidden by constructors and can never be called");
1188 errorSupplemental(fcall
->loc
, "Please use a factory method instead, or replace all constructors with static opCall.");
1193 if (global
.errors
!= errors
)
1195 // The type is no good.
1196 type
= Type::terror
;
1197 this->errors
= true;
1199 deferred
->errors
= true;
1202 if (deferred
&& !global
.gag
)
1204 deferred
->semantic2(sc
);
1205 deferred
->semantic3(sc
);
1208 assert(type
->ty
!= Tstruct
|| ((TypeStruct
*)type
)->sym
== this);
1211 Dsymbol
*StructDeclaration::search(const Loc
&loc
, Identifier
*ident
, int flags
)
1213 //printf("%s.StructDeclaration::search('%s', flags = x%x)\n", toChars(), ident->toChars(), flags);
1215 if (_scope
&& !symtab
)
1218 if (!members
|| !symtab
) // opaque or semantic() is not yet called
1220 error("is forward referenced when looking for '%s'", ident
->toChars());
1224 return ScopeDsymbol::search(loc
, ident
, flags
);
1227 void StructDeclaration::finalizeSize()
1229 //printf("StructDeclaration::finalizeSize() %s, sizeok = %d\n", toChars(), sizeok);
1230 assert(sizeok
!= SIZEOKdone
);
1232 //printf("+StructDeclaration::finalizeSize() %s, fields.dim = %d, sizeok = %d\n", toChars(), fields.dim, sizeok);
1234 fields
.setDim(0); // workaround
1236 // Set the offsets of the fields and determine the size of the struct
1237 unsigned offset
= 0;
1238 bool isunion
= isUnionDeclaration() != NULL
;
1239 for (size_t i
= 0; i
< members
->dim
; i
++)
1241 Dsymbol
*s
= (*members
)[i
];
1242 s
->setFieldOffset(this, &offset
, isunion
);
1244 if (type
->ty
== Terror
)
1247 // 0 sized struct's are set to 1 byte
1248 if (structsize
== 0)
1254 // Round struct size up to next alignsize boundary.
1255 // This will ensure that arrays of structs will get their internals
1256 // aligned properly.
1257 if (alignment
== STRUCTALIGN_DEFAULT
)
1258 structsize
= (structsize
+ alignsize
- 1) & ~(alignsize
- 1);
1260 structsize
= (structsize
+ alignment
- 1) & ~(alignment
- 1);
1262 sizeok
= SIZEOKdone
;
1264 //printf("-StructDeclaration::finalizeSize() %s, fields.dim = %d, structsize = %d\n", toChars(), fields.dim, structsize);
1269 // Calculate fields[i]->overlapped
1270 if (checkOverlappedFields())
1276 // Determine if struct is all zeros or not
1278 for (size_t i
= 0; i
< fields
.dim
; i
++)
1280 VarDeclaration
*vd
= fields
[i
];
1283 // Should examine init to see if it is really all 0's
1287 else if (!vd
->type
->isZeroInit(loc
))
1294 TypeTuple
*tt
= toArgTypes(type
);
1295 size_t dim
= tt
->arguments
->dim
;
1299 arg1type
= (*tt
->arguments
)[0]->type
;
1301 arg2type
= (*tt
->arguments
)[1]->type
;
1305 /***************************************
1306 * Fit elements[] to the corresponding type of field[].
1310 * elements The explicit arguments that given to construct object.
1311 * stype The constructed object type.
1312 * Returns false if any errors occur.
1313 * Otherwise, returns true and elements[] are rewritten for the output.
1315 bool StructDeclaration::fit(Loc loc
, Scope
*sc
, Expressions
*elements
, Type
*stype
)
1320 size_t nfields
= fields
.dim
- isNested();
1322 for (size_t i
= 0; i
< elements
->dim
; i
++)
1324 Expression
*e
= (*elements
)[i
];
1328 e
= resolveProperties(sc
, e
);
1331 if (i
== fields
.dim
- 1 && isNested() && e
->op
== TOKnull
)
1333 // CTFE sometimes creates null as hidden pointer; we'll allow this.
1336 ::error(loc
, "more initializers than fields (%d) of %s", (int)nfields
, toChars());
1339 VarDeclaration
*v
= fields
[i
];
1340 if (v
->offset
< offset
)
1342 ::error(loc
, "overlapping initialization for %s", v
->toChars());
1345 offset
= (unsigned)(v
->offset
+ v
->type
->size());
1349 t
= t
->addMod(stype
->mod
);
1351 Type
*tb
= t
->toBasetype();
1353 /* Look for case of initializing a static array with a too-short
1354 * string literal, such as:
1355 * char[5] foo = "abc";
1356 * Allow this by doing an explicit cast, which will lengthen the string
1359 if (e
->op
== TOKstring
&& tb
->ty
== Tsarray
)
1361 StringExp
*se
= (StringExp
*)e
;
1362 Type
*typeb
= se
->type
->toBasetype();
1363 TY tynto
= tb
->nextOf()->ty
;
1364 if (!se
->committed
&&
1365 (typeb
->ty
== Tarray
|| typeb
->ty
== Tsarray
) &&
1366 (tynto
== Tchar
|| tynto
== Twchar
|| tynto
== Tdchar
) &&
1367 se
->numberOfCodeUnits(tynto
) < ((TypeSArray
*)tb
)->dim
->toInteger())
1369 e
= se
->castTo(sc
, t
);
1374 while (!e
->implicitConvTo(t
) && tb
->ty
== Tsarray
)
1376 /* Static array initialization, as in:
1380 tb
= t
->toBasetype();
1382 if (!e
->implicitConvTo(t
))
1383 t
= origType
; // restore type for better diagnostic
1385 e
= e
->implicitCastTo(sc
, t
);
1387 if (e
->op
== TOKerror
)
1390 (*elements
)[i
] = doCopyOrMove(sc
, e
);
1395 /***************************************
1396 * Return true if struct is POD (Plain Old Data).
1397 * This is defined as:
1399 * no postblits, destructors, or assignment operators
1400 * no 'ref' fields or fields that are themselves non-POD
1401 * The idea being these are compatible with C structs.
1403 bool StructDeclaration::isPOD()
1405 // If we've already determined whether this struct is POD.
1406 if (ispod
!= ISPODfwd
)
1407 return (ispod
== ISPODyes
);
1411 if (enclosing
|| postblit
|| dtor
)
1414 // Recursively check all fields are POD.
1415 for (size_t i
= 0; i
< fields
.dim
; i
++)
1417 VarDeclaration
*v
= fields
[i
];
1418 if (v
->storage_class
& STCref
)
1424 Type
*tv
= v
->type
->baseElemOf();
1425 if (tv
->ty
== Tstruct
)
1427 TypeStruct
*ts
= (TypeStruct
*)tv
;
1428 StructDeclaration
*sd
= ts
->sym
;
1437 return (ispod
== ISPODyes
);
1440 const char *StructDeclaration::kind() const
1445 /********************************* UnionDeclaration ****************************/
1447 UnionDeclaration::UnionDeclaration(Loc loc
, Identifier
*id
)
1448 : StructDeclaration(loc
, id
, false)
1452 Dsymbol
*UnionDeclaration::syntaxCopy(Dsymbol
*s
)
1455 UnionDeclaration
*ud
= new UnionDeclaration(loc
, ident
);
1456 return StructDeclaration::syntaxCopy(ud
);
1459 const char *UnionDeclaration::kind() const