Skip to content

Commit

Permalink
Merge pull request #3174 from 9rnsr/fix12023
Browse files Browse the repository at this point in the history
[REG2.065a] Issue 12023 - template mixin fails within template class
  • Loading branch information
yebblies committed Jan 29, 2014
2 parents 152c680 + 244c5ac commit 257562e
Show file tree
Hide file tree
Showing 2 changed files with 87 additions and 55 deletions.
98 changes: 43 additions & 55 deletions src/expression.c
Expand Up @@ -3396,15 +3396,7 @@ Expression *DsymbolExp::semantic(Scope *sc)
#endif

Lagain:
EnumMember *em;
Expression *e;
VarDeclaration *v;
FuncDeclaration *f;
FuncLiteralDeclaration *fld;
OverloadSet *o;
Import *imp;
Package *pkg;
Type *t;

//printf("DsymbolExp:: %p '%s' is a symbol\n", this, toChars());
//printf("s = '%s', s->kind = '%s'\n", s->toChars(), s->kind());
Expand All @@ -3416,40 +3408,45 @@ Expression *DsymbolExp::semantic(Scope *sc)
if (s != olds && !s->isFuncDeclaration())
checkDeprecated(sc, s);

// BUG: This should happen after overload resolution for functions, not before
if (s->needThis())
if (VarDeclaration *v = s->isVarDeclaration())
{
if (hasThis(sc) && !s->isFuncDeclaration())
/* Bugzilla 12023: forward reference should be resolved
* before 's->needThis()' is called.
*/
if ((!v->type || !v->type->deco) && v->scope)
{
v->semantic(v->scope);
s = v->toAlias(); // Need this if 'v' is a tuple variable
}
}
if (s->needThis() && hasThis(sc))
{
// For functions, this should happen after overload resolution
if (!s->isFuncDeclaration())
{
// Supply an implicit 'this', as in
// this.ident

DotVarExp *de;

de = new DotVarExp(loc, new ThisExp(loc), s->isDeclaration());
DotVarExp *de = new DotVarExp(loc, new ThisExp(loc), s->isDeclaration());
return de->semantic(sc);
}
}

em = s->isEnumMember();
if (em)
if (EnumMember *em = s->isEnumMember())
{
return em->getVarExp(loc, sc);
}
v = s->isVarDeclaration();
if (v)
if (VarDeclaration *v = s->isVarDeclaration())
{
//printf("Identifier '%s' is a variable, type '%s'\n", toChars(), v->type->toChars());
if (!type)
{ if ((!v->type || !v->type->deco) && v->scope)
v->semantic(v->scope);
{
type = v->type;
if (!v->type)
{ error("forward reference of %s %s", s->kind(), s->toChars());
{
error("forward reference of %s %s", s->kind(), s->toChars());
return new ErrorExp();
}
}

if ((v->storage_class & STCmanifest) && v->init)
{
if (v->scope)
Expand All @@ -3461,7 +3458,8 @@ Expression *DsymbolExp::semantic(Scope *sc)
}
e = v->init->toExpression(v->type);
if (!e)
{ error("cannot make expression out of initializer for %s", v->toChars());
{
error("cannot make expression out of initializer for %s", v->toChars());
return new ErrorExp();
}
e = e->copy();
Expand All @@ -3475,14 +3473,13 @@ Expression *DsymbolExp::semantic(Scope *sc)
e = e->semantic(sc);
return e->deref();
}
fld = s->isFuncLiteralDeclaration();
if (fld)
{ //printf("'%s' is a function literal\n", fld->toChars());
if (FuncLiteralDeclaration *fld = s->isFuncLiteralDeclaration())
{
//printf("'%s' is a function literal\n", fld->toChars());
e = new FuncExp(loc, fld);
return e->semantic(sc);
}
f = s->isFuncDeclaration();
if (f)
if (FuncDeclaration *f = s->isFuncDeclaration())
{
f = f->toAliasFunc();
if (!f->functionSemantic())
Expand All @@ -3497,56 +3494,49 @@ Expression *DsymbolExp::semantic(Scope *sc)
fd->type = f->type;
return new VarExp(loc, fd, hasOverloads);
}
o = s->isOverloadSet();
if (o)
{ //printf("'%s' is an overload set\n", o->toChars());
if (OverloadSet *o = s->isOverloadSet())
{
//printf("'%s' is an overload set\n", o->toChars());
return new OverExp(loc, o);
}
imp = s->isImport();
if (imp)

if (Import *imp = s->isImport())
{
if (!imp->pkg)
{ error("forward reference of import %s", imp->toChars());
{
error("forward reference of import %s", imp->toChars());
return new ErrorExp();
}
ScopeExp *ie = new ScopeExp(loc, imp->pkg);
return ie->semantic(sc);
}
pkg = s->isPackage();
if (pkg)
if (Package *pkg = s->isPackage())
{
ScopeExp *ie;

ie = new ScopeExp(loc, pkg);
ScopeExp *ie = new ScopeExp(loc, pkg);
return ie->semantic(sc);
}
Module *mod = s->isModule();
if (mod)
if (Module *mod = s->isModule())
{
ScopeExp *ie;

ie = new ScopeExp(loc, mod);
ScopeExp *ie = new ScopeExp(loc, mod);
return ie->semantic(sc);
}

t = s->getType();
if (t)
if (Type *t = s->getType())
{
TypeExp *te = new TypeExp(loc, t);
return te->semantic(sc);
}

TupleDeclaration *tup = s->isTupleDeclaration();
if (tup)
if (TupleDeclaration *tup = s->isTupleDeclaration())
{
e = new TupleExp(loc, tup);
e = e->semantic(sc);
return e;
}

TemplateInstance *ti = s->isTemplateInstance();
if (ti)
{ if (!ti->semanticRun)
if (TemplateInstance *ti = s->isTemplateInstance())
{
if (!ti->semanticRun)
ti->semantic(sc);
s = ti->toAlias();
if (!s->isTemplateInstance())
Expand All @@ -3557,9 +3547,7 @@ Expression *DsymbolExp::semantic(Scope *sc)
e = e->semantic(sc);
return e;
}

TemplateDeclaration *td = s->isTemplateDeclaration();
if (td)
if (TemplateDeclaration *td = s->isTemplateDeclaration())
{
Dsymbol *p = td->toParent2();
FuncDeclaration *fdthis = hasThis(sc);
Expand Down
44 changes: 44 additions & 0 deletions test/runnable/mixin1.d
Expand Up @@ -3,6 +3,8 @@ module mixin1;

import std.stdio;

alias TypeTuple(T...) = T;

/*******************************************/

mixin template Foo(T)
Expand Down Expand Up @@ -1259,6 +1261,47 @@ void test11767()
static assert(!__traits(compiles, S11767));
}

/*******************************************/
// 12023

void Delete12023(Object obj) {}

template MessageCode12023()
{
alias typeof(this) C;

struct MessageDeinitHelper
{
C m_outer;

~this()
{
m_outer.DoDeinitMessaging();
}
}

CToClient toClient = null;
TypeTuple!(CToClient) toClients;

class CToClient {}

void DoDeinitMessaging()
{
Delete12023(toClient);
Delete12023(toClients);
}
}

class TurretCannon12023(ProjectileClass)
{
mixin MessageCode12023;
}

void test12023()
{
auto tc = new TurretCannon12023!Object();
}

/*******************************************/

int main()
Expand Down Expand Up @@ -1309,6 +1352,7 @@ int main()
test42();
test9417();
test11767();
test12023();

printf("Success\n");
return 0;
Expand Down

0 comments on commit 257562e

Please sign in to comment.