Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merge upstream stable (dlang/dmd@cf518229cf) #3593

Merged
merged 1 commit into from
Oct 23, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 1 addition & 2 deletions dmd/dimport.d
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@ import dmd.expression;
import dmd.globals;
import dmd.identifier;
import dmd.mtype;
import dmd.root.rmem;
import dmd.visitor;

/***********************************************************
Expand Down Expand Up @@ -266,7 +265,7 @@ extern (C++) final class Import : Dsymbol
Identifier _alias = aliases[i];
if (!_alias)
_alias = name;
auto tname = Pool!TypeIdentifier.make(loc, name);
auto tname = new TypeIdentifier(loc, name);
auto ad = new AliasDeclaration(loc, _alias, tname);
ad._import = this;
ad.addMember(sc, sd);
Expand Down
67 changes: 52 additions & 15 deletions dmd/dsymbolsem.d
Original file line number Diff line number Diff line change
Expand Up @@ -4144,7 +4144,7 @@ version (IN_LLVM)
if (cmainTemplateExists())
{
// add `mixin _d_cmain!();` to the declaring module
auto tqual = Pool!TypeIdentifier.make(funcdecl.loc, Id.CMain);
auto tqual = new TypeIdentifier(funcdecl.loc, Id.CMain);
auto tm = new TemplateMixin(funcdecl.loc, null, tqual, null);
sc._module.members.push(tm);
}
Expand Down Expand Up @@ -5971,17 +5971,6 @@ void templateInstanceSemantic(TemplateInstance tempinst, Scope* sc, Expressions*
{
tempinst.minst = null;
}
// https://issues.dlang.org/show_bug.cgi?id=21299
// If not speculative, this instance should have the same instantiating
// root module as its enclosing template symbol. This can differ when
// the enclosing template gets changed from non-root to a root instance
// in the instantiation graph. When that occurs, this instance also
// needs to be appended to the root module, otherwise there will be
// undefined references at link-time.
if (tempinst.minst && tempinst.tinst)
{
tempinst.minst = tempinst.tinst.minst;
}

tempinst.gagged = (global.gag > 0);

Expand Down Expand Up @@ -6100,17 +6089,18 @@ void templateInstanceSemantic(TemplateInstance tempinst, Scope* sc, Expressions*
if (tempinst.minst && tempinst.minst.isRoot() && !(tempinst.inst.minst && tempinst.inst.minst.isRoot()))
{
/* Swap the position of 'inst' and 'this' in the instantiation graph.
* Then, the primary instance `inst` will be changed to a root instance.
* Then, the primary instance `inst` will be changed to a root instance,
* along with all members of `inst` having their scopes updated.
*
* Before:
* non-root -> A!() -> B!()[inst] -> C!()
* non-root -> A!() -> B!()[inst] -> C!() { members[non-root] }
* |
* root -> D!() -> B!()[this]
*
* After:
* non-root -> A!() -> B!()[this]
* |
* root -> D!() -> B!()[inst] -> C!()
* root -> D!() -> B!()[inst] -> C!() { members[root] }
*/
Module mi = tempinst.minst;
TemplateInstance ti = tempinst.tinst;
Expand All @@ -6119,6 +6109,53 @@ void templateInstanceSemantic(TemplateInstance tempinst, Scope* sc, Expressions*
tempinst.inst.minst = mi;
tempinst.inst.tinst = ti;

/* https://issues.dlang.org/show_bug.cgi?id=21299
`minst` has been updated on the primary instance `inst` so it is
now coming from a root module, however all Dsymbol `inst.members`
of the instance still have their `_scope.minst` pointing at the
original non-root module. We must now propagate `minst` to all
members so that forward referenced dependencies that get
instantiated will also be appended to the root module, otherwise
there will be undefined references at link-time. */
extern (C++) final class InstMemberWalker : Visitor
{
alias visit = Visitor.visit;
TemplateInstance inst;

extern (D) this(TemplateInstance inst)
{
this.inst = inst;
}

override void visit(Dsymbol d)
{
if (d._scope)
d._scope.minst = inst.minst;
}

override void visit(ScopeDsymbol sds)
{
sds.members.foreachDsymbol( s => s.accept(this) );
visit(cast(Dsymbol)sds);
}

override void visit(AttribDeclaration ad)
{
ad.include(null).foreachDsymbol( s => s.accept(this) );
visit(cast(Dsymbol)ad);
}

override void visit(ConditionalDeclaration cd)
{
if (cd.condition.inc)
visit(cast(AttribDeclaration)cd);
else
visit(cast(Dsymbol)cd);
}
}
scope v = new InstMemberWalker(tempinst.inst);
tempinst.inst.accept(v);

if (tempinst.minst) // if inst was not speculative
{
/* Add 'inst' once again to the root module members[], then the
Expand Down
59 changes: 17 additions & 42 deletions dmd/dtemplate.d
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,6 @@ import dmd.mtype;
import dmd.opover;
import dmd.root.array;
import dmd.root.outbuffer;
import dmd.root.rmem;
import dmd.root.rootobject;
import dmd.semantic2;
import dmd.semantic3;
Expand Down Expand Up @@ -1523,7 +1522,8 @@ else
if (auto ttp = param.isTemplateThisParameter())
{
hasttp = true;
scope t = new TypeIdentifier(Loc.initial, ttp.ident);

Type t = new TypeIdentifier(Loc.initial, ttp.ident);
MATCH m = deduceType(tthis, paramscope, t, parameters, dedtypes);
if (m <= MATCH.nomatch)
goto Lnomatch;
Expand Down Expand Up @@ -2849,23 +2849,17 @@ void functionResolve(ref MatchAccumulator m, Dsymbol dstart, Loc loc, Scope* sc,
{
if (!tiargs)
tiargs = new Objects();
auto ti = Pool!TemplateInstance.make(loc, td, tiargs);
auto ti = new TemplateInstance(loc, td, tiargs);
Objects dedtypes = Objects(td.parameters.dim);
assert(td.semanticRun != PASS.init);
MATCH mta = td.matchWithInstance(sc, ti, &dedtypes, fargs, 0);
//printf("matchWithInstance = %d\n", mta);
if (mta <= MATCH.nomatch || mta < ta_last) // no match or less match
{
Pool!TemplateInstance.dispose(ti);
return 0;
}

ti.templateInstanceSemantic(sc, fargs);
if (!ti.inst) // if template failed to expand
{
Pool!TemplateInstance.dispose(ti);
return 0;
}

Dsymbol s = ti.inst.toAlias();
FuncDeclaration fd;
Expand All @@ -2888,7 +2882,6 @@ void functionResolve(ref MatchAccumulator m, Dsymbol dstart, Loc loc, Scope* sc,
if (scx == p.sc)
{
error(loc, "recursive template expansion while looking for `%s.%s`", ti.toChars(), tdx.toChars());
Pool!TemplateInstance.dispose(ti);
goto Lerror;
}
}
Expand Down Expand Up @@ -2922,7 +2915,6 @@ void functionResolve(ref MatchAccumulator m, Dsymbol dstart, Loc loc, Scope* sc,
m.lastf = fd; // to propagate "error match"
m.count = 1;
m.last = MATCH.nomatch;
Pool!TemplateInstance.dispose(ti);
return 1;
}

Expand All @@ -2946,7 +2938,6 @@ void functionResolve(ref MatchAccumulator m, Dsymbol dstart, Loc loc, Scope* sc,
return 0;

Ltd_best2:
Pool!TemplateInstance.dispose(ti);
return 0;

Ltd2:
Expand All @@ -2973,7 +2964,7 @@ void functionResolve(ref MatchAccumulator m, Dsymbol dstart, Loc loc, Scope* sc,

/* This is a 'dummy' instance to evaluate constraint properly.
*/
auto ti = Pool!TemplateInstance.make(loc, td, tiargs);
auto ti = new TemplateInstance(loc, td, tiargs);
ti.parent = td.parent; // Maybe calculating valid 'enclosing' is unnecessary.

auto fd = f;
Expand All @@ -2982,10 +2973,7 @@ void functionResolve(ref MatchAccumulator m, Dsymbol dstart, Loc loc, Scope* sc,
MATCH mfa = cast(MATCH)(x & 0xF);
//printf("match:t/f = %d/%d\n", mta, mfa);
if (!fd || mfa == MATCH.nomatch)
{
Pool!TemplateInstance.dispose(ti);
continue;
}

Type tthis_fd = fd.needThis() ? tthis : null;

Expand Down Expand Up @@ -3103,14 +3091,12 @@ void functionResolve(ref MatchAccumulator m, Dsymbol dstart, Loc loc, Scope* sc,
if (!sc)
sc = td_best._scope; // workaround for Type.aliasthisOf

auto ti = Pool!TemplateInstance.make(loc, td_best, ti_best.tiargs);
auto ti = new TemplateInstance(loc, td_best, ti_best.tiargs);
ti.templateInstanceSemantic(sc, fargs);

m.lastf = ti.toAlias().isFuncDeclaration();
if (!m.lastf)
{
goto Lnomatch;
}
if (ti.errors)
{
Lerror:
Expand Down Expand Up @@ -4071,12 +4057,11 @@ MATCH deduceType(RootObject o, Scope* sc, Type tparam, TemplateParameters* param
* it up and seeing if is an alias.
* https://issues.dlang.org/show_bug.cgi?id=1454
*/
auto tid = Pool!TypeIdentifier.make(tp.loc, tp.tempinst.name);
auto tid = new TypeIdentifier(tp.loc, tp.tempinst.name);
Type tx;
Expression e;
Dsymbol s;
tid.resolve(tp.loc, sc, &e, &tx, &s);
Pool!TypeIdentifier.dispose(tid);
if (tx)
{
s = tx.toDsymbol(sc);
Expand Down Expand Up @@ -4855,17 +4840,16 @@ MATCH deduceType(RootObject o, Scope* sc, Type tparam, TemplateParameters* param
if (!tf.next && tof.next)
e.fd.treq = tparam;

auto ti = Pool!TemplateInstance.make(e.loc, e.td, tiargs);
auto ti = new TemplateInstance(e.loc, e.td, tiargs);
Expression ex = (new ScopeExp(e.loc, ti)).expressionSemantic(e.td._scope);

// Reset inference target for the later re-semantic
e.fd.treq = null;

if (ex.op == TOK.error)
return;
if (ex.op != TOK.function_)
{
Pool!TemplateInstance.dispose(ti);
return;
}
visit(ex.type);
return;
}
Expand Down Expand Up @@ -5416,12 +5400,9 @@ extern (C++) class TemplateTypeParameter : TemplateParameter
override final bool declareParameter(Scope* sc)
{
//printf("TemplateTypeParameter.declareParameter('%s')\n", ident.toChars());
auto ti = Pool!TypeIdentifier.make(loc, ident);
auto ti = new TypeIdentifier(loc, ident);
Declaration ad = new AliasDeclaration(loc, ident, ti);
if (sc.insert(ad) !is null)
return true;
Pool!TypeIdentifier.dispose(ti);
return false;
return sc.insert(ad) !is null;
}

override final void print(RootObject oarg, RootObject oded)
Expand Down Expand Up @@ -5468,7 +5449,7 @@ extern (C++) class TemplateTypeParameter : TemplateParameter
{
// Use this for alias-parameter's too (?)
if (!tdummy)
tdummy = Pool!TypeIdentifier.make(loc, ident);
tdummy = new TypeIdentifier(loc, ident);
t = tdummy;
}
return t;
Expand Down Expand Up @@ -5645,12 +5626,9 @@ extern (C++) final class TemplateAliasParameter : TemplateParameter

override bool declareParameter(Scope* sc)
{
auto ti = Pool!TypeIdentifier.make(loc, ident);
auto ti = new TypeIdentifier(loc, ident);
Declaration ad = new AliasDeclaration(loc, ident, ti);
if (sc.insert(ad) !is null)
return true;
Pool!TypeIdentifier.dispose(ti);
return false;
return sc.insert(ad) !is null;
}

override void print(RootObject oarg, RootObject oded)
Expand Down Expand Up @@ -5730,12 +5708,9 @@ extern (C++) final class TemplateTupleParameter : TemplateParameter

override bool declareParameter(Scope* sc)
{
auto ti = Pool!TypeIdentifier.make(loc, ident);
auto ti = new TypeIdentifier(loc, ident);
Declaration ad = new AliasDeclaration(loc, ident, ti);
if (sc.insert(ad) !is null)
return true;
Pool!TypeIdentifier.dispose(ti);
return false;
return sc.insert(ad) !is null;
}

override void print(RootObject oarg, RootObject oded)
Expand Down Expand Up @@ -5915,7 +5890,7 @@ extern (C++) class TemplateInstance : ScopeDsymbol

override Dsymbol syntaxCopy(Dsymbol s)
{
TemplateInstance ti = s ? cast(TemplateInstance)s : Pool!TemplateInstance.make(loc, name, null);
TemplateInstance ti = s ? cast(TemplateInstance)s : new TemplateInstance(loc, name, null);
ti.tiargs = arraySyntaxCopy(tiargs);
TemplateDeclaration td;
if (inst && tempdecl && (td = tempdecl.isTemplateDeclaration()) !is null)
Expand Down
4 changes: 2 additions & 2 deletions dmd/expression.d
Original file line number Diff line number Diff line change
Expand Up @@ -3967,7 +3967,7 @@ extern (C++) final class FuncExp : Expression
if (!tf.next && tof.next)
fd.treq = to;

auto ti = Pool!TemplateInstance.make(loc, td, tiargs);
auto ti = new TemplateInstance(loc, td, tiargs);
Expression ex = (new ScopeExp(loc, ti)).expressionSemantic(td._scope);

// Reset inference target for the later re-semantic
Expand Down Expand Up @@ -4899,7 +4899,7 @@ extern (C++) final class DotTemplateInstanceExp : UnaExp
{
super(loc, TOK.dotTemplateInstance, __traits(classInstanceSize, DotTemplateInstanceExp), e);
//printf("DotTemplateInstanceExp()\n");
this.ti = Pool!TemplateInstance.make(loc, name, tiargs);
this.ti = new TemplateInstance(loc, name, tiargs);
}

extern (D) this(const ref Loc loc, Expression e, TemplateInstance ti)
Expand Down
12 changes: 9 additions & 3 deletions dmd/expressionsem.d
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,6 @@ import dmd.root.ctfloat;
import dmd.root.file;
import dmd.root.filename;
import dmd.root.outbuffer;
import dmd.root.rmem;
import dmd.root.rootobject;
import dmd.root.string;
import dmd.semantic2;
Expand Down Expand Up @@ -466,7 +465,7 @@ private Expression searchUFCS(Scope* sc, UnaExp ue, Identifier ident)
if (ue.op == TOK.dotTemplateInstance)
{
DotTemplateInstanceExp dti = cast(DotTemplateInstanceExp)ue;
auto ti = Pool!TemplateInstance.make(loc, s.ident, dti.ti.tiargs);
auto ti = new TemplateInstance(loc, s.ident, dti.ti.tiargs);
if (!ti.updateTempDecl(sc, s))
return ErrorExp.get();
return new ScopeExp(loc, ti);
Expand Down Expand Up @@ -1440,6 +1439,13 @@ private bool arrayExpressionToCommonType(Scope* sc, Expressions* exps, Type* pt)
Expression ex = condexp.expressionSemantic(sc);
if (ex.op == TOK.error)
e = ex;
else if (e.op == TOK.function_ || e.op == TOK.delegate_)
{
// https://issues.dlang.org/show_bug.cgi?id=21285
// Functions and delegates don't convert correctly with castTo below
(*exps)[j0] = condexp.e1;
e = condexp.e2;
}
else
{
// Convert to common type
Expand Down Expand Up @@ -4172,7 +4178,7 @@ private extern (C++) final class ExpressionSemanticVisitor : Visitor
}
}

auto ti = Pool!TemplateInstance.make(exp.loc, exp.td, tiargs);
auto ti = new TemplateInstance(exp.loc, exp.td, tiargs);
return (new ScopeExp(exp.loc, ti)).expressionSemantic(sc);
}
return exp.expressionSemantic(sc);
Expand Down
2 changes: 1 addition & 1 deletion dmd/mtype.d
Original file line number Diff line number Diff line change
Expand Up @@ -5562,7 +5562,7 @@ extern (C++) final class TypeIdentifier : TypeQualified

override Type syntaxCopy()
{
auto t = Pool!TypeIdentifier.make(loc, ident);
auto t = new TypeIdentifier(loc, ident);
t.syntaxCopyHelper(this);
t.mod = mod;
return t;
Expand Down
Loading