1
2 /* Compiler implementation of the D programming language
3 * Copyright (C) 1999-2019 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 */
9
10 #include "root/checkedint.h"
11 #include "mars.h"
12 #include "init.h"
13 #include "expression.h"
14 #include "statement.h"
15 #include "declaration.h"
16 #include "aggregate.h"
17 #include "scope.h"
18 #include "mtype.h"
19 #include "template.h"
20 #include "id.h"
21
22 FuncDeclaration *isFuncAddress(Expression *e, bool *hasOverloads = NULL);
23 Expression *semantic(Expression *e, Scope *sc);
24 Initializer *inferType(Initializer *init, Scope *sc);
25 Initializer *semantic(Initializer *init, Scope *sc, Type *t, NeedInterpret needInterpret);
26 bool hasNonConstPointers(Expression *e);
27
28 class InitializerSemanticVisitor : public Visitor
29 {
30 public:
31 Initializer *result;
32 Scope *sc;
33 Type *t;
34 NeedInterpret needInterpret;
35
InitializerSemanticVisitor(Scope * sc,Type * t,NeedInterpret needInterpret)36 InitializerSemanticVisitor(Scope *sc, Type *t, NeedInterpret needInterpret)
37 {
38 this->result = NULL;
39 this->sc = sc;
40 this->t = t;
41 this->needInterpret = needInterpret;
42 }
43
visit(ErrorInitializer * i)44 void visit(ErrorInitializer *i)
45 {
46 //printf("ErrorInitializer::semantic(t = %p)\n", t);
47 result = i;
48 }
49
visit(VoidInitializer * i)50 void visit(VoidInitializer *i)
51 {
52 //printf("VoidInitializer::semantic(t = %p)\n", t);
53 i->type = t;
54 result = i;
55 }
56
visit(StructInitializer * i)57 void visit(StructInitializer *i)
58 {
59 //printf("StructInitializer::semantic(t = %s) %s\n", t->toChars(), toChars());
60 t = t->toBasetype();
61 if (t->ty == Tsarray && t->nextOf()->toBasetype()->ty == Tstruct)
62 t = t->nextOf()->toBasetype();
63 if (t->ty == Tstruct)
64 {
65 StructDeclaration *sd = ((TypeStruct *)t)->sym;
66 if (sd->ctor)
67 {
68 error(i->loc, "%s %s has constructors, cannot use { initializers }, use %s( initializers ) instead",
69 sd->kind(), sd->toChars(), sd->toChars());
70 result = new ErrorInitializer();
71 return;
72 }
73 sd->size(i->loc);
74 if (sd->sizeok != SIZEOKdone)
75 {
76 result = new ErrorInitializer();
77 return;
78 }
79 size_t nfields = sd->fields.dim - sd->isNested();
80
81 //expandTuples for non-identity arguments?
82
83 Expressions *elements = new Expressions();
84 elements->setDim(nfields);
85 for (size_t j = 0; j < elements->dim; j++)
86 (*elements)[j] = NULL;
87
88 // Run semantic for explicitly given initializers
89 // TODO: this part is slightly different from StructLiteralExp::semantic.
90 bool errors = false;
91 for (size_t fieldi = 0, j = 0; j < i->field.dim; j++)
92 {
93 if (Identifier *id = i->field[j])
94 {
95 Dsymbol *s = sd->search(i->loc, id);
96 if (!s)
97 {
98 s = sd->search_correct(id);
99 if (s)
100 error(i->loc, "'%s' is not a member of '%s', did you mean %s '%s'?",
101 id->toChars(), sd->toChars(), s->kind(), s->toChars());
102 else
103 error(i->loc, "'%s' is not a member of '%s'", id->toChars(), sd->toChars());
104 result = new ErrorInitializer();
105 return;
106 }
107 s = s->toAlias();
108
109 // Find out which field index it is
110 for (fieldi = 0; 1; fieldi++)
111 {
112 if (fieldi >= nfields)
113 {
114 error(i->loc, "%s.%s is not a per-instance initializable field",
115 sd->toChars(), s->toChars());
116 result = new ErrorInitializer();
117 return;
118 }
119 if (s == sd->fields[fieldi])
120 break;
121 }
122 }
123 else if (fieldi >= nfields)
124 {
125 error(i->loc, "too many initializers for %s", sd->toChars());
126 result = new ErrorInitializer();
127 return;
128 }
129
130 VarDeclaration *vd = sd->fields[fieldi];
131 if ((*elements)[fieldi])
132 {
133 error(i->loc, "duplicate initializer for field '%s'", vd->toChars());
134 errors = true;
135 continue;
136 }
137 for (size_t k = 0; k < nfields; k++)
138 {
139 VarDeclaration *v2 = sd->fields[k];
140 if (vd->isOverlappedWith(v2) && (*elements)[k])
141 {
142 error(i->loc, "overlapping initialization for field %s and %s",
143 v2->toChars(), vd->toChars());
144 errors = true;
145 continue;
146 }
147 }
148
149 assert(sc);
150 Initializer *iz = i->value[j];
151 iz = ::semantic(iz, sc, vd->type->addMod(t->mod), needInterpret);
152 Expression *ex = initializerToExpression(iz);
153 if (ex->op == TOKerror)
154 {
155 errors = true;
156 continue;
157 }
158 i->value[j] = iz;
159 (*elements)[fieldi] = doCopyOrMove(sc, ex);
160 ++fieldi;
161 }
162 if (errors)
163 {
164 result = new ErrorInitializer();
165 return;
166 }
167
168 StructLiteralExp *sle = new StructLiteralExp(i->loc, sd, elements, t);
169 if (!sd->fill(i->loc, elements, false))
170 {
171 result = new ErrorInitializer();
172 return;
173 }
174 sle->type = t;
175
176 ExpInitializer *ie = new ExpInitializer(i->loc, sle);
177 result = ::semantic(ie, sc, t, needInterpret);
178 return;
179 }
180 else if ((t->ty == Tdelegate || (t->ty == Tpointer && t->nextOf()->ty == Tfunction)) && i->value.dim == 0)
181 {
182 TOK tok = (t->ty == Tdelegate) ? TOKdelegate : TOKfunction;
183 /* Rewrite as empty delegate literal { }
184 */
185 Parameters *parameters = new Parameters;
186 Type *tf = new TypeFunction(parameters, NULL, 0, LINKd);
187 FuncLiteralDeclaration *fd = new FuncLiteralDeclaration(i->loc, Loc(), tf, tok, NULL);
188 fd->fbody = new CompoundStatement(i->loc, new Statements());
189 fd->endloc = i->loc;
190 Expression *e = new FuncExp(i->loc, fd);
191 ExpInitializer *ie = new ExpInitializer(i->loc, e);
192 result = ::semantic(ie, sc, t, needInterpret);
193 return;
194 }
195
196 error(i->loc, "a struct is not a valid initializer for a %s", t->toChars());
197 result = new ErrorInitializer();
198 }
199
visit(ArrayInitializer * i)200 void visit(ArrayInitializer *i)
201 {
202 unsigned length;
203 const unsigned amax = 0x80000000;
204 bool errors = false;
205
206 //printf("ArrayInitializer::semantic(%s)\n", t->toChars());
207 if (i->sem) // if semantic() already run
208 {
209 result = i;
210 return;
211 }
212 i->sem = true;
213 t = t->toBasetype();
214 switch (t->ty)
215 {
216 case Tsarray:
217 case Tarray:
218 break;
219
220 case Tvector:
221 t = ((TypeVector *)t)->basetype;
222 break;
223
224 case Taarray:
225 case Tstruct: // consider implicit constructor call
226 {
227 Expression *e;
228 // note: MyStruct foo = [1:2, 3:4] is correct code if MyStruct has a this(int[int])
229 if (t->ty == Taarray || i->isAssociativeArray())
230 e = i->toAssocArrayLiteral();
231 else
232 e = initializerToExpression(i);
233 if (!e) // Bugzilla 13987
234 {
235 error(i->loc, "cannot use array to initialize %s", t->toChars());
236 goto Lerr;
237 }
238 ExpInitializer *ei = new ExpInitializer(e->loc, e);
239 result = ::semantic(ei, sc, t, needInterpret);
240 return;
241 }
242 case Tpointer:
243 if (t->nextOf()->ty != Tfunction)
244 break;
245 /* fall through */
246
247 default:
248 error(i->loc, "cannot use array to initialize %s", t->toChars());
249 goto Lerr;
250 }
251
252 i->type = t;
253
254 length = 0;
255 for (size_t j = 0; j < i->index.dim; j++)
256 {
257 Expression *idx = i->index[j];
258 if (idx)
259 {
260 sc = sc->startCTFE();
261 idx = ::semantic(idx, sc);
262 sc = sc->endCTFE();
263 idx = idx->ctfeInterpret();
264 i->index[j] = idx;
265 const uinteger_t idxvalue = idx->toInteger();
266 if (idxvalue >= amax)
267 {
268 error(i->loc, "array index %llu overflow", (ulonglong)idxvalue);
269 errors = true;
270 }
271 length = (unsigned)idx->toInteger();
272 if (idx->op == TOKerror)
273 errors = true;
274 }
275
276 Initializer *val = i->value[j];
277 ExpInitializer *ei = val->isExpInitializer();
278 if (ei && !idx)
279 ei->expandTuples = true;
280 val = ::semantic(val, sc, t->nextOf(), needInterpret);
281 if (val->isErrorInitializer())
282 errors = true;
283
284 ei = val->isExpInitializer();
285 // found a tuple, expand it
286 if (ei && ei->exp->op == TOKtuple)
287 {
288 TupleExp *te = (TupleExp *)ei->exp;
289 i->index.remove(j);
290 i->value.remove(j);
291
292 for (size_t k = 0; k < te->exps->dim; ++k)
293 {
294 Expression *e = (*te->exps)[k];
295 i->index.insert(j + k, (Expression *)NULL);
296 i->value.insert(j + k, new ExpInitializer(e->loc, e));
297 }
298 j--;
299 continue;
300 }
301 else
302 {
303 i->value[j] = val;
304 }
305
306 length++;
307 if (length == 0)
308 {
309 error(i->loc, "array dimension overflow");
310 goto Lerr;
311 }
312 if (length > i->dim)
313 i->dim = length;
314 }
315 if (t->ty == Tsarray)
316 {
317 uinteger_t edim = ((TypeSArray *)t)->dim->toInteger();
318 if (i->dim > edim)
319 {
320 error(i->loc, "array initializer has %u elements, but array length is %llu", i->dim, (ulonglong)edim);
321 goto Lerr;
322 }
323 }
324 if (errors)
325 goto Lerr;
326 else
327 {
328 d_uns64 sz = t->nextOf()->size();
329 bool overflow = false;
330 const d_uns64 max = mulu((d_uns64)i->dim, sz, overflow);
331 if (overflow || max > amax)
332 {
333 error(i->loc, "array dimension %llu exceeds max of %llu", (ulonglong)i->dim, (ulonglong)(amax / sz));
334 goto Lerr;
335 }
336 result = i;
337 return;
338 }
339
340 Lerr:
341 result = new ErrorInitializer();
342 }
343
visit(ExpInitializer * i)344 void visit(ExpInitializer *i)
345 {
346 //printf("ExpInitializer::semantic(%s), type = %s\n", i->exp->toChars(), t->toChars());
347 if (needInterpret) sc = sc->startCTFE();
348 i->exp = ::semantic(i->exp, sc);
349 i->exp = resolveProperties(sc, i->exp);
350 if (needInterpret) sc = sc->endCTFE();
351 if (i->exp->op == TOKerror)
352 {
353 result = new ErrorInitializer();
354 return;
355 }
356
357 unsigned int olderrors = global.errors;
358 if (needInterpret)
359 {
360 // If the result will be implicitly cast, move the cast into CTFE
361 // to avoid premature truncation of polysemous types.
362 // eg real [] x = [1.1, 2.2]; should use real precision.
363 if (i->exp->implicitConvTo(t))
364 {
365 i->exp = i->exp->implicitCastTo(sc, t);
366 }
367 if (!global.gag && olderrors != global.errors)
368 {
369 result = i;
370 return;
371 }
372 i->exp = i->exp->ctfeInterpret();
373 }
374 else
375 {
376 i->exp = i->exp->optimize(WANTvalue);
377 }
378 if (!global.gag && olderrors != global.errors)
379 {
380 result = i; // Failed, suppress duplicate error messages
381 return;
382 }
383
384 if (i->exp->type->ty == Ttuple && ((TypeTuple *)i->exp->type)->arguments->dim == 0)
385 {
386 Type *et = i->exp->type;
387 i->exp = new TupleExp(i->exp->loc, new Expressions());
388 i->exp->type = et;
389 }
390 if (i->exp->op == TOKtype)
391 {
392 i->exp->error("initializer must be an expression, not '%s'", i->exp->toChars());
393 result = new ErrorInitializer();
394 return;
395 }
396
397 // Make sure all pointers are constants
398 if (needInterpret && hasNonConstPointers(i->exp))
399 {
400 i->exp->error("cannot use non-constant CTFE pointer in an initializer '%s'", i->exp->toChars());
401 result = new ErrorInitializer();
402 return;
403 }
404
405 Type *tb = t->toBasetype();
406 Type *ti = i->exp->type->toBasetype();
407
408 if (i->exp->op == TOKtuple && i->expandTuples && !i->exp->implicitConvTo(t))
409 {
410 result = new ExpInitializer(i->loc, i->exp);
411 return;
412 }
413
414 /* Look for case of initializing a static array with a too-short
415 * string literal, such as:
416 * char[5] foo = "abc";
417 * Allow this by doing an explicit cast, which will lengthen the string
418 * literal.
419 */
420 if (i->exp->op == TOKstring && tb->ty == Tsarray)
421 {
422 StringExp *se = (StringExp *)i->exp;
423 Type *typeb = se->type->toBasetype();
424 TY tynto = tb->nextOf()->ty;
425 if (!se->committed &&
426 (typeb->ty == Tarray || typeb->ty == Tsarray) &&
427 (tynto == Tchar || tynto == Twchar || tynto == Tdchar) &&
428 se->numberOfCodeUnits(tynto) < ((TypeSArray *)tb)->dim->toInteger())
429 {
430 i->exp = se->castTo(sc, t);
431 goto L1;
432 }
433 }
434
435 // Look for implicit constructor call
436 if (tb->ty == Tstruct &&
437 !(ti->ty == Tstruct && tb->toDsymbol(sc) == ti->toDsymbol(sc)) &&
438 !i->exp->implicitConvTo(t))
439 {
440 StructDeclaration *sd = ((TypeStruct *)tb)->sym;
441 if (sd->ctor)
442 {
443 // Rewrite as S().ctor(exp)
444 Expression *e;
445 e = new StructLiteralExp(i->loc, sd, NULL);
446 e = new DotIdExp(i->loc, e, Id::ctor);
447 e = new CallExp(i->loc, e, i->exp);
448 e = ::semantic(e, sc);
449 if (needInterpret)
450 i->exp = e->ctfeInterpret();
451 else
452 i->exp = e->optimize(WANTvalue);
453 }
454 }
455
456 // Look for the case of statically initializing an array
457 // with a single member.
458 if (tb->ty == Tsarray &&
459 !tb->nextOf()->equals(ti->toBasetype()->nextOf()) &&
460 i->exp->implicitConvTo(tb->nextOf())
461 )
462 {
463 /* If the variable is not actually used in compile time, array creation is
464 * redundant. So delay it until invocation of toExpression() or toDt().
465 */
466 t = tb->nextOf();
467 }
468
469 if (i->exp->implicitConvTo(t))
470 {
471 i->exp = i->exp->implicitCastTo(sc, t);
472 }
473 else
474 {
475 // Look for mismatch of compile-time known length to emit
476 // better diagnostic message, as same as AssignExp::semantic.
477 if (tb->ty == Tsarray &&
478 i->exp->implicitConvTo(tb->nextOf()->arrayOf()) > MATCHnomatch)
479 {
480 uinteger_t dim1 = ((TypeSArray *)tb)->dim->toInteger();
481 uinteger_t dim2 = dim1;
482 if (i->exp->op == TOKarrayliteral)
483 {
484 ArrayLiteralExp *ale = (ArrayLiteralExp *)i->exp;
485 dim2 = ale->elements ? ale->elements->dim : 0;
486 }
487 else if (i->exp->op == TOKslice)
488 {
489 Type *tx = toStaticArrayType((SliceExp *)i->exp);
490 if (tx)
491 dim2 = ((TypeSArray *)tx)->dim->toInteger();
492 }
493 if (dim1 != dim2)
494 {
495 i->exp->error("mismatched array lengths, %d and %d", (int)dim1, (int)dim2);
496 i->exp = new ErrorExp();
497 }
498 }
499 i->exp = i->exp->implicitCastTo(sc, t);
500 }
501 L1:
502 if (i->exp->op == TOKerror)
503 {
504 result = i;
505 return;
506 }
507 if (needInterpret)
508 i->exp = i->exp->ctfeInterpret();
509 else
510 i->exp = i->exp->optimize(WANTvalue);
511 //printf("-ExpInitializer::semantic(): "); i->exp->print();
512 result = i;
513 }
514 };
515
516 // Performs semantic analisys on Initializer AST nodes
semantic(Initializer * init,Scope * sc,Type * t,NeedInterpret needInterpret)517 Initializer *semantic(Initializer *init, Scope *sc, Type *t, NeedInterpret needInterpret)
518 {
519 InitializerSemanticVisitor v = InitializerSemanticVisitor(sc, t, needInterpret);
520 init->accept(&v);
521 return v.result;
522 }
523
524 class InferTypeVisitor : public Visitor
525 {
526 public:
527 Initializer *result;
528 Scope *sc;
529
InferTypeVisitor(Scope * sc)530 InferTypeVisitor(Scope *sc)
531 {
532 this->result = NULL;
533 this->sc = sc;
534 }
535
visit(ErrorInitializer * i)536 void visit(ErrorInitializer *i)
537 {
538 result = i;
539 }
540
visit(VoidInitializer * i)541 void visit(VoidInitializer *i)
542 {
543 error(i->loc, "cannot infer type from void initializer");
544 result = new ErrorInitializer();
545 }
546
visit(StructInitializer * i)547 void visit(StructInitializer *i)
548 {
549 error(i->loc, "cannot infer type from struct initializer");
550 result = new ErrorInitializer();
551 }
552
visit(ArrayInitializer * init)553 void visit(ArrayInitializer *init)
554 {
555 //printf("ArrayInitializer::inferType() %s\n", init->toChars());
556 Expressions *keys = NULL;
557 Expressions *values;
558 if (init->isAssociativeArray())
559 {
560 keys = new Expressions();
561 keys->setDim(init->value.dim);
562 values = new Expressions();
563 values->setDim(init->value.dim);
564
565 for (size_t i = 0; i < init->value.dim; i++)
566 {
567 Expression *e = init->index[i];
568 if (!e)
569 goto Lno;
570 (*keys)[i] = e;
571
572 Initializer *iz = init->value[i];
573 if (!iz)
574 goto Lno;
575 iz = inferType(iz, sc);
576 if (iz->isErrorInitializer())
577 {
578 result = iz;
579 return;
580 }
581 assert(iz->isExpInitializer());
582 (*values)[i] = ((ExpInitializer *)iz)->exp;
583 assert((*values)[i]->op != TOKerror);
584 }
585
586 Expression *e = new AssocArrayLiteralExp(init->loc, keys, values);
587 ExpInitializer *ei = new ExpInitializer(init->loc, e);
588 result = inferType(ei, sc);
589 return;
590 }
591 else
592 {
593 Expressions *elements = new Expressions();
594 elements->setDim(init->value.dim);
595 elements->zero();
596
597 for (size_t i = 0; i < init->value.dim; i++)
598 {
599 assert(!init->index[i]); // already asserted by isAssociativeArray()
600
601 Initializer *iz = init->value[i];
602 if (!iz)
603 goto Lno;
604 iz = inferType(iz, sc);
605 if (iz->isErrorInitializer())
606 {
607 result = iz;
608 return;
609 }
610 assert(iz->isExpInitializer());
611 (*elements)[i] = ((ExpInitializer *)iz)->exp;
612 assert((*elements)[i]->op != TOKerror);
613 }
614
615 Expression *e = new ArrayLiteralExp(init->loc, NULL, elements);
616 ExpInitializer *ei = new ExpInitializer(init->loc, e);
617 result = inferType(ei, sc);
618 return;
619 }
620 Lno:
621 if (keys)
622 {
623 delete keys;
624 delete values;
625 error(init->loc, "not an associative array initializer");
626 }
627 else
628 {
629 error(init->loc, "cannot infer type from array initializer");
630 }
631 result = new ErrorInitializer();
632 }
633
visit(ExpInitializer * init)634 void visit(ExpInitializer *init)
635 {
636 //printf("ExpInitializer::inferType() %s\n", init->toChars());
637 init->exp = ::semantic(init->exp, sc);
638 init->exp = resolveProperties(sc, init->exp);
639
640 if (init->exp->op == TOKscope)
641 {
642 ScopeExp *se = (ScopeExp *)init->exp;
643 TemplateInstance *ti = se->sds->isTemplateInstance();
644 if (ti && ti->semanticRun == PASSsemantic && !ti->aliasdecl)
645 se->error("cannot infer type from %s %s, possible circular dependency", se->sds->kind(), se->toChars());
646 else
647 se->error("cannot infer type from %s %s", se->sds->kind(), se->toChars());
648 result = new ErrorInitializer();
649 return;
650 }
651
652 // Give error for overloaded function addresses
653 bool hasOverloads = false;
654 if (FuncDeclaration *f = isFuncAddress(init->exp, &hasOverloads))
655 {
656 if (f->checkForwardRef(init->loc))
657 {
658 result = new ErrorInitializer();
659 return;
660 }
661
662 if (hasOverloads && !f->isUnique())
663 {
664 init->exp->error("cannot infer type from overloaded function symbol %s", init->exp->toChars());
665 result = new ErrorInitializer();
666 return;
667 }
668 }
669 if (init->exp->op == TOKaddress)
670 {
671 AddrExp *ae = (AddrExp *)init->exp;
672 if (ae->e1->op == TOKoverloadset)
673 {
674 init->exp->error("cannot infer type from overloaded function symbol %s", init->exp->toChars());
675 result = new ErrorInitializer();
676 return;
677 }
678 }
679
680 if (init->exp->op == TOKerror)
681 {
682 result = new ErrorInitializer();
683 return;
684 }
685 if (!init->exp->type)
686 {
687 result = new ErrorInitializer();
688 return;
689 }
690 result = init;
691 }
692 };
693
694 /* Translates to an expression to infer type.
695 * Returns ExpInitializer or ErrorInitializer.
696 */
inferType(Initializer * init,Scope * sc)697 Initializer *inferType(Initializer *init, Scope *sc)
698 {
699 InferTypeVisitor v = InferTypeVisitor(sc);
700 init->accept(&v);
701 return v.result;
702 }
703
704 class InitToExpressionVisitor : public Visitor
705 {
706 public:
707 Expression *result;
708 Type *itype;
709
InitToExpressionVisitor(Type * itype)710 InitToExpressionVisitor(Type *itype)
711 {
712 this->result = NULL;
713 this->itype = itype;
714 }
715
visit(ErrorInitializer *)716 void visit(ErrorInitializer *)
717 {
718 result = new ErrorExp();
719 }
720
visit(VoidInitializer *)721 void visit(VoidInitializer *)
722 {
723 result = NULL;
724 }
725
726 /***************************************
727 * This works by transforming a struct initializer into
728 * a struct literal. In the future, the two should be the
729 * same thing.
730 */
visit(StructInitializer *)731 void visit(StructInitializer *)
732 {
733 // cannot convert to an expression without target 'ad'
734 result = NULL;
735 }
736
737 /********************************
738 * If possible, convert array initializer to array literal.
739 * Otherwise return NULL.
740 */
741
visit(ArrayInitializer * init)742 void visit(ArrayInitializer *init)
743 {
744 //printf("ArrayInitializer::toExpression(), dim = %d\n", init->dim);
745 //static int i; if (++i == 2) halt();
746
747 Expressions *elements;
748 unsigned edim;
749 const unsigned amax = 0x80000000;
750 Type *t = NULL;
751 if (init->type)
752 {
753 if (init->type == Type::terror)
754 {
755 result = new ErrorExp();
756 return;
757 }
758
759 t = init->type->toBasetype();
760 switch (t->ty)
761 {
762 case Tvector:
763 t = ((TypeVector *)t)->basetype;
764 /* fall through */
765
766 case Tsarray:
767 {
768 uinteger_t adim = ((TypeSArray *)t)->dim->toInteger();
769 if (adim >= amax)
770 goto Lno;
771 edim = (unsigned)adim;
772 break;
773 }
774
775 case Tpointer:
776 case Tarray:
777 edim = init->dim;
778 break;
779
780 default:
781 assert(0);
782 }
783 }
784 else
785 {
786 edim = (unsigned)init->value.dim;
787 for (size_t i = 0, j = 0; i < init->value.dim; i++, j++)
788 {
789 if (init->index[i])
790 {
791 if (init->index[i]->op == TOKint64)
792 {
793 const uinteger_t idxval = init->index[i]->toInteger();
794 if (idxval >= amax)
795 goto Lno;
796 j = (size_t)idxval;
797 }
798 else
799 goto Lno;
800 }
801 if (j >= edim)
802 edim = (unsigned)(j + 1);
803 }
804 }
805
806 elements = new Expressions();
807 elements->setDim(edim);
808 elements->zero();
809 for (size_t i = 0, j = 0; i < init->value.dim; i++, j++)
810 {
811 if (init->index[i])
812 j = (size_t)(init->index[i])->toInteger();
813 assert(j < edim);
814 Initializer *iz = init->value[i];
815 if (!iz)
816 goto Lno;
817 Expression *ex = initializerToExpression(iz);
818 if (!ex)
819 {
820 goto Lno;
821 }
822 (*elements)[j] = ex;
823 }
824
825 /* Fill in any missing elements with the default initializer
826 */
827 {
828 Expression *_init = NULL;
829 for (size_t i = 0; i < edim; i++)
830 {
831 if (!(*elements)[i])
832 {
833 if (!init->type)
834 goto Lno;
835 if (!_init)
836 _init = ((TypeNext *)t)->next->defaultInit();
837 (*elements)[i] = _init;
838 }
839 }
840
841 /* Expand any static array initializers that are a single expression
842 * into an array of them
843 */
844 if (t)
845 {
846 Type *tn = t->nextOf()->toBasetype();
847 if (tn->ty == Tsarray)
848 {
849 size_t dim = ((TypeSArray *)tn)->dim->toInteger();
850 Type *te = tn->nextOf()->toBasetype();
851 for (size_t i = 0; i < elements->dim; i++)
852 {
853 Expression *e = (*elements)[i];
854 if (te->equals(e->type))
855 {
856 Expressions *elements2 = new Expressions();
857 elements2->setDim(dim);
858 for (size_t j = 0; j < dim; j++)
859 (*elements2)[j] = e;
860 e = new ArrayLiteralExp(e->loc, tn, elements2);
861 (*elements)[i] = e;
862 }
863 }
864 }
865 }
866
867 /* If any elements are errors, then the whole thing is an error
868 */
869 for (size_t i = 0; i < edim; i++)
870 {
871 Expression *e = (*elements)[i];
872 if (e->op == TOKerror)
873 {
874 result = e;
875 return;
876 }
877 }
878
879 Expression *e = new ArrayLiteralExp(init->loc, init->type, elements);
880 result = e;
881 return;
882 }
883
884 Lno:
885 result = NULL;
886 }
887
visit(ExpInitializer * i)888 void visit(ExpInitializer *i)
889 {
890 if (itype)
891 {
892 //printf("ExpInitializer::toExpression(t = %s) exp = %s\n", itype->toChars(), i->exp->toChars());
893 Type *tb = itype->toBasetype();
894 Expression *e = (i->exp->op == TOKconstruct || i->exp->op == TOKblit) ? ((AssignExp *)i->exp)->e2 : i->exp;
895 if (tb->ty == Tsarray && e->implicitConvTo(tb->nextOf()))
896 {
897 TypeSArray *tsa = (TypeSArray *)tb;
898 size_t d = (size_t)tsa->dim->toInteger();
899 Expressions *elements = new Expressions();
900 elements->setDim(d);
901 for (size_t i = 0; i < d; i++)
902 (*elements)[i] = e;
903 ArrayLiteralExp *ae = new ArrayLiteralExp(e->loc, itype, elements);
904 result = ae;
905 return;
906 }
907 }
908 result = i->exp;
909 }
910 };
911
initializerToExpression(Initializer * i,Type * t)912 Expression *initializerToExpression(Initializer *i, Type *t)
913 {
914 InitToExpressionVisitor v = InitToExpressionVisitor(t);
915 i->accept(&v);
916 return v.result;
917 }
918