Skip to content

Commit

Permalink
Merged pull request #44 from donc/structinit2.
Browse files Browse the repository at this point in the history
Second round of struct initializer bugs
  • Loading branch information
WalterBright committed Apr 28, 2011
2 parents 48950d4 + fa4b0a9 commit 13dcf90
Show file tree
Hide file tree
Showing 6 changed files with 55 additions and 27 deletions.
10 changes: 5 additions & 5 deletions src/declaration.c
Original file line number Diff line number Diff line change
Expand Up @@ -322,7 +322,7 @@ void TypedefDeclaration::semantic2(Scope *sc)
{ sem = Semantic2Done;
if (init)
{
init = init->semantic(sc, basetype);
init = init->semantic(sc, basetype, WANTinterpret);

ExpInitializer *ie = init->isExpInitializer();
if (ie)
Expand Down Expand Up @@ -1100,7 +1100,7 @@ void VarDeclaration::semantic(Scope *sc)
Expression *e = init->toExpression();
if (!e)
{
init = init->semantic(sc, type);
init = init->semantic(sc, type, 0); // Don't need to interpret
e = init->toExpression();
if (!e)
{ error("is not a static and cannot have static initializer");
Expand Down Expand Up @@ -1238,7 +1238,7 @@ void VarDeclaration::semantic(Scope *sc)
}
else
{
init = init->semantic(sc, type);
init = init->semantic(sc, type, WANTinterpret);
}
}
else if (storage_class & (STCconst | STCimmutable | STCmanifest) ||
Expand Down Expand Up @@ -1311,7 +1311,7 @@ void VarDeclaration::semantic(Scope *sc)
}
else if (si || ai)
{ i2 = init->syntaxCopy();
i2 = i2->semantic(sc, type);
i2 = i2->semantic(sc, type, WANTinterpret);
}
inuse--;
global.gag--;
Expand Down Expand Up @@ -1392,7 +1392,7 @@ void VarDeclaration::semantic2(Scope *sc)
printf("type = %p\n", ei->exp->type);
}
#endif
init = init->semantic(sc, type);
init = init->semantic(sc, type, WANTinterpret);
inuse--;
}
sem = Semantic2Done;
Expand Down
2 changes: 1 addition & 1 deletion src/expression.c
Original file line number Diff line number Diff line change
Expand Up @@ -3462,7 +3462,7 @@ Expression *StructLiteralExp::semantic(Scope *sc)
else if (v->scope)
{ // Do deferred semantic analysis
Initializer *i2 = v->init->syntaxCopy();
i2 = i2->semantic(v->scope, v->type);
i2 = i2->semantic(v->scope, v->type, WANTinterpret);
e = i2->toExpression();
v->scope = NULL;
}
Expand Down
25 changes: 15 additions & 10 deletions src/init.c
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ Initializer *Initializer::syntaxCopy()
return this;
}

Initializer *Initializer::semantic(Scope *sc, Type *t)
Initializer *Initializer::semantic(Scope *sc, Type *t, int needInterpret)
{
return this;
}
Expand Down Expand Up @@ -87,7 +87,7 @@ Initializer *VoidInitializer::syntaxCopy()
}


Initializer *VoidInitializer::semantic(Scope *sc, Type *t)
Initializer *VoidInitializer::semantic(Scope *sc, Type *t, int needInterpret)
{
//printf("VoidInitializer::semantic(t = %p)\n", t);
type = t;
Expand Down Expand Up @@ -141,7 +141,7 @@ void StructInitializer::addInit(Identifier *field, Initializer *value)
this->value.push(value);
}

Initializer *StructInitializer::semantic(Scope *sc, Type *t)
Initializer *StructInitializer::semantic(Scope *sc, Type *t, int needInterpret)
{
int errors = 0;

Expand Down Expand Up @@ -205,7 +205,7 @@ Initializer *StructInitializer::semantic(Scope *sc, Type *t)
}
if (s && (v = s->isVarDeclaration()) != NULL)
{
val = val->semantic(sc, v->type);
val = val->semantic(sc, v->type, needInterpret);
value.data[i] = (void *)val;
vars.data[i] = (void *)v;
}
Expand All @@ -226,7 +226,7 @@ Initializer *StructInitializer::semantic(Scope *sc, Type *t)
fd->endloc = loc;
Expression *e = new FuncExp(loc, fd);
ExpInitializer *ie = new ExpInitializer(loc, e);
return ie->semantic(sc, t);
return ie->semantic(sc, t, needInterpret);
}
else
{
Expand Down Expand Up @@ -416,7 +416,7 @@ void ArrayInitializer::addInit(Expression *index, Initializer *value)
type = NULL;
}

Initializer *ArrayInitializer::semantic(Scope *sc, Type *t)
Initializer *ArrayInitializer::semantic(Scope *sc, Type *t, int needInterpret)
{ unsigned i;
unsigned length;
const unsigned amax = 0x80000000;
Expand Down Expand Up @@ -451,7 +451,7 @@ Initializer *ArrayInitializer::semantic(Scope *sc, Type *t)
}

Initializer *val = (Initializer *)value.data[i];
val = val->semantic(sc, t->nextOf());
val = val->semantic(sc, t->nextOf(), needInterpret);
value.data[i] = (void *)val;
length++;
if (length == 0)
Expand Down Expand Up @@ -706,12 +706,17 @@ Initializer *ExpInitializer::syntaxCopy()
return new ExpInitializer(loc, exp->syntaxCopy());
}

Initializer *ExpInitializer::semantic(Scope *sc, Type *t)
Initializer *ExpInitializer::semantic(Scope *sc, Type *t, int needInterpret)
{
//printf("ExpInitializer::semantic(%s), type = %s\n", exp->toChars(), t->toChars());
exp = exp->semantic(sc);
exp = resolveProperties(sc, exp);
exp = exp->optimize(WANTvalue | WANTinterpret);
int wantOptimize = needInterpret ? WANTinterpret|WANTvalue : WANTvalue;

int olderrors = global.errors;
exp = exp->optimize(wantOptimize);
if (!global.gag && olderrors != global.errors)
return this; // Failed, suppress duplicate error messages
Type *tb = t->toBasetype();

/* Look for case of initializing a static array with a too-short
Expand Down Expand Up @@ -744,7 +749,7 @@ Initializer *ExpInitializer::semantic(Scope *sc, Type *t)

exp = exp->implicitCastTo(sc, t);
L1:
exp = exp->optimize(WANTvalue | WANTinterpret);
exp = exp->optimize(wantOptimize);
//printf("-ExpInitializer::semantic(): "); exp->print();
return this;
}
Expand Down
11 changes: 6 additions & 5 deletions src/init.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,8 @@ struct Initializer : Object

Initializer(Loc loc);
virtual Initializer *syntaxCopy();
virtual Initializer *semantic(Scope *sc, Type *t);
// needInterpret is WANTinterpret if must be a manifest constant, 0 if not.
virtual Initializer *semantic(Scope *sc, Type *t, int needInterpret);
virtual Type *inferType(Scope *sc);
virtual Expression *toExpression() = 0;
virtual void toCBuffer(OutBuffer *buf, HdrGenState *hgs) = 0;
Expand All @@ -58,7 +59,7 @@ struct VoidInitializer : Initializer

VoidInitializer(Loc loc);
Initializer *syntaxCopy();
Initializer *semantic(Scope *sc, Type *t);
Initializer *semantic(Scope *sc, Type *t, int needInterpret);
Expression *toExpression();
void toCBuffer(OutBuffer *buf, HdrGenState *hgs);

Expand All @@ -78,7 +79,7 @@ struct StructInitializer : Initializer
StructInitializer(Loc loc);
Initializer *syntaxCopy();
void addInit(Identifier *field, Initializer *value);
Initializer *semantic(Scope *sc, Type *t);
Initializer *semantic(Scope *sc, Type *t, int needInterpret);
Expression *toExpression();
void toCBuffer(OutBuffer *buf, HdrGenState *hgs);

Expand All @@ -98,7 +99,7 @@ struct ArrayInitializer : Initializer
ArrayInitializer(Loc loc);
Initializer *syntaxCopy();
void addInit(Expression *index, Initializer *value);
Initializer *semantic(Scope *sc, Type *t);
Initializer *semantic(Scope *sc, Type *t, int needInterpret);
int isAssociativeArray();
Type *inferType(Scope *sc);
Expression *toExpression();
Expand All @@ -117,7 +118,7 @@ struct ExpInitializer : Initializer

ExpInitializer(Loc loc, Expression *exp);
Initializer *syntaxCopy();
Initializer *semantic(Scope *sc, Type *t);
Initializer *semantic(Scope *sc, Type *t, int needInterpret);
Type *inferType(Scope *sc);
Expression *toExpression();
void toCBuffer(OutBuffer *buf, HdrGenState *hgs);
Expand Down
23 changes: 18 additions & 5 deletions src/interpret.c
Original file line number Diff line number Diff line change
Expand Up @@ -1292,10 +1292,23 @@ Expression *getVarExp(Loc loc, InterState *istate, Declaration *d, CtfeGoal goal
if (v->isConst() && v->init)
#endif
{ e = v->init->toExpression();
if (e && !e->type)
e->type = v->type;
if (e)
if (e && (e->op == TOKconstruct || e->op == TOKblit))
{ AssignExp *ae = (AssignExp *)e;
e = ae->e2;
v->inuse++;
e = e->interpret(istate, ctfeNeedAnyValue);
v->inuse--;
if (e == EXP_CANT_INTERPRET)
return e;
e->type = v->type;
}
else
{
if (e && !e->type)
e->type = v->type;
if (e)
e = e->interpret(istate, ctfeNeedAnyValue);
}
if (e && e != EXP_CANT_INTERPRET)
v->setValueWithoutChecking(e);
}
Expand Down Expand Up @@ -1339,10 +1352,10 @@ Expression *getVarExp(Loc loc, InterState *istate, Declaration *d, CtfeGoal goal
e = EXP_CANT_INTERPRET;
}
else if (s)
{
{ // Struct static initializers, for example
if (s->dsym->toInitializer() == s->sym)
{ Expressions *exps = new Expressions();
e = new StructLiteralExp(0, s->dsym, exps);
e = new StructLiteralExp(loc, s->dsym, exps);
e = e->semantic(NULL);
if (e->op == TOKerror)
e = EXP_CANT_INTERPRET;
Expand Down
11 changes: 10 additions & 1 deletion src/optimize.c
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,16 @@ Expression *expandVar(int result, VarDeclaration *v)
}
else if (ei->isConst() != 1 && ei->op != TOKstring)
goto L1;
if (ei->type != v->type)

if (ei->type == v->type)
{ // const variable initialized with const expression
}
else if (ei->implicitConvTo(v->type) >= MATCHconst)
{ // const var initialized with non-const expression
ei = ei->implicitCastTo(0, v->type);
ei = ei->semantic(0);
}
else
goto L1;
}
if (v->scope)
Expand Down

0 comments on commit 13dcf90

Please sign in to comment.