Skip to content

Commit a9efb98

Browse files
WalterBrightdlang-bot
authored andcommitted
ImportC add simple array initialization
1 parent f1692f5 commit a9efb98

File tree

3 files changed

+75
-4
lines changed

3 files changed

+75
-4
lines changed

src/dmd/initsem.d

+38-3
Original file line numberDiff line numberDiff line change
@@ -559,11 +559,46 @@ extern(C++) Initializer initializerSemantic(Initializer init, Scope* sc, ref Typ
559559
return i;
560560
}
561561

562-
Initializer visitC(CInitializer i)
562+
Initializer visitC(CInitializer ci)
563563
{
564564
//printf("CInitializer::semantic()\n");
565-
error(i.loc, "C initializers not supported yet");
566-
return err();
565+
t = t.toBasetype();
566+
auto tsa = t.isTypeSArray();
567+
if (!tsa)
568+
{
569+
error(ci.loc, "C non-static-array initializers not supported yet");
570+
return err();
571+
}
572+
573+
const uint amax = 0x8000_0000;
574+
bool errors;
575+
auto tn = tsa.nextOf();
576+
auto dil = ci.initializerList[];
577+
foreach (di; dil)
578+
{
579+
if (di.designatorList)
580+
{
581+
error(ci.loc, "C designator-list not supported yet");
582+
return err();
583+
}
584+
di.initializer = di.initializer.initializerSemantic(sc, tn, needInterpret);
585+
if (di.initializer.isErrorInitializer())
586+
errors = true;
587+
}
588+
589+
if (errors)
590+
return err();
591+
592+
const sz = tn.size();
593+
bool overflow;
594+
const max = mulu(dil.length, sz, overflow);
595+
if (overflow || max >= amax)
596+
{
597+
error(ci.loc, "array dimension %llu exceeds max of %llu", ulong(dil.length), ulong(amax / sz));
598+
return err();
599+
}
600+
601+
return ci;
567602
}
568603

569604
final switch (init.kind)

src/dmd/todt.d

+15-1
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,9 @@ extern (C++) void Initializer_toDt(Initializer init, ref DtBuilder dtb)
7979

8080
void visitStruct(StructInitializer si)
8181
{
82+
/* The StructInitializer was converted to a StructLiteralExp,
83+
* which is converted to dtb by membersToDt()
84+
*/
8285
//printf("StructInitializer.toDt('%s')\n", si.toChars());
8386
assert(0);
8487
}
@@ -197,14 +200,25 @@ extern (C++) void Initializer_toDt(Initializer init, ref DtBuilder dtb)
197200
Expression_toDt(ei.exp, dtb);
198201
}
199202

203+
void visitC(CInitializer ci)
204+
{
205+
//printf("CInitializer::semantic()\n");
206+
auto dil = ci.initializerList[];
207+
foreach (di; dil)
208+
{
209+
assert(!di.designatorList);
210+
Initializer_toDt(di.initializer, dtb);
211+
}
212+
}
213+
200214
final switch (init.kind)
201215
{
202216
case InitKind.void_: return visitVoid (cast( VoidInitializer)init);
203217
case InitKind.error: return visitError (cast( ErrorInitializer)init);
204218
case InitKind.struct_: return visitStruct(cast(StructInitializer)init);
205219
case InitKind.array: return visitArray (cast( ArrayInitializer)init);
206220
case InitKind.exp: return visitExp (cast( ExpInitializer)init);
207-
case InitKind.C_: assert(0);
221+
case InitKind.C_: return visitC (cast( CInitializer)init);
208222
}
209223
}
210224

test/runnable/cstuff2.c

+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
2+
int printf(const char *, ...);
3+
void exit(int);
4+
5+
void test1()
6+
{
7+
static int a[3] = {1, 2, 3};
8+
if (a[0] != 1 ||
9+
a[1] != 2 ||
10+
a[2] != 3)
11+
{
12+
printf("error 1\n");
13+
exit(1);
14+
}
15+
}
16+
17+
int main()
18+
{
19+
test1();
20+
return 0;
21+
}
22+

0 commit comments

Comments
 (0)