diff --git a/src/cast.c b/src/cast.c index b30fc820efe0..9d6aa4af6810 100644 --- a/src/cast.c +++ b/src/cast.c @@ -1825,15 +1825,18 @@ Expression *SliceExp::castTo(Scope *sc, Type *t) /**************************************** * Set type inference target + * t Target type * flag 1: don't put an error when inference fails + * sc it is used for the semantic of t, when != NULL + * tparams template parameters should be inferred */ -Expression *Expression::inferType(Type *t, int flag, TemplateParameters *tparams) +Expression *Expression::inferType(Type *t, int flag, Scope *sc, TemplateParameters *tparams) { return this; } -Expression *ArrayLiteralExp::inferType(Type *t, int flag, TemplateParameters *tparams) +Expression *ArrayLiteralExp::inferType(Type *t, int flag, Scope *sc, TemplateParameters *tparams) { if (t) { @@ -1844,7 +1847,7 @@ Expression *ArrayLiteralExp::inferType(Type *t, int flag, TemplateParameters *tp for (size_t i = 0; i < elements->dim; i++) { Expression *e = (*elements)[i]; if (e) - { e = e->inferType(tn, flag, tparams); + { e = e->inferType(tn, flag, sc, tparams); (*elements)[i] = e; } } @@ -1853,7 +1856,7 @@ Expression *ArrayLiteralExp::inferType(Type *t, int flag, TemplateParameters *tp return this; } -Expression *AssocArrayLiteralExp::inferType(Type *t, int flag, TemplateParameters *tparams) +Expression *AssocArrayLiteralExp::inferType(Type *t, int flag, Scope *sc, TemplateParameters *tparams) { if (t) { @@ -1865,14 +1868,14 @@ Expression *AssocArrayLiteralExp::inferType(Type *t, int flag, TemplateParameter for (size_t i = 0; i < keys->dim; i++) { Expression *e = (*keys)[i]; if (e) - { e = e->inferType(ti, flag, tparams); + { e = e->inferType(ti, flag, sc, tparams); (*keys)[i] = e; } } for (size_t i = 0; i < values->dim; i++) { Expression *e = (*values)[i]; if (e) - { e = e->inferType(tv, flag, tparams); + { e = e->inferType(tv, flag, sc, tparams); (*values)[i] = e; } } @@ -1881,7 +1884,7 @@ Expression *AssocArrayLiteralExp::inferType(Type *t, int flag, TemplateParameter return this; } -Expression *FuncExp::inferType(Type *to, int flag, TemplateParameters *tparams) +Expression *FuncExp::inferType(Type *to, int flag, Scope *sc, TemplateParameters *tparams) { if (!to) return this; @@ -1939,7 +1942,10 @@ Expression *FuncExp::inferType(Type *to, int flag, TemplateParameters *tparams) Type *tprm = p->type; if (tprm->reliesOnTident(tparams)) goto L1; - tprm = tprm->semantic(loc, td->scope); + if (sc) + tprm = tprm->semantic(loc, sc); + if (tprm->ty == Terror) + goto L1; tiargs->push(tprm); u = dim; // break inner loop } @@ -1995,13 +2001,13 @@ Expression *FuncExp::inferType(Type *to, int flag, TemplateParameters *tparams) return e; } -Expression *CondExp::inferType(Type *t, int flag, TemplateParameters *tparams) +Expression *CondExp::inferType(Type *t, int flag, Scope *sc, TemplateParameters *tparams) { if (t) { t = t->toBasetype(); - e1 = e1->inferType(t, flag, tparams); - e2 = e2->inferType(t, flag, tparams); + e1 = e1->inferType(t, flag, sc, tparams); + e2 = e2->inferType(t, flag, sc, tparams); } return this; } diff --git a/src/expression.h b/src/expression.h index 944ffd99ef10..102a1717e62c 100644 --- a/src/expression.h +++ b/src/expression.h @@ -142,7 +142,7 @@ struct Expression : Object virtual MATCH implicitConvTo(Type *t); virtual IntRange getIntRange(); virtual Expression *castTo(Scope *sc, Type *t); - virtual Expression *inferType(Type *t, int flag = 0, TemplateParameters *tparams = NULL); + virtual Expression *inferType(Type *t, int flag = 0, Scope *sc = NULL, TemplateParameters *tparams = NULL); virtual void checkEscape(); virtual void checkEscapeRef(); virtual Expression *resolveLoc(Loc loc, Scope *sc); @@ -452,7 +452,7 @@ struct ArrayLiteralExp : Expression Expression *interpret(InterState *istate, CtfeGoal goal = ctfeNeedRvalue); MATCH implicitConvTo(Type *t); Expression *castTo(Scope *sc, Type *t); - Expression *inferType(Type *t, int flag = 0, TemplateParameters *tparams = NULL); + Expression *inferType(Type *t, int flag = 0, Scope *sc = NULL, TemplateParameters *tparams = NULL); dt_t **toDt(dt_t **pdt); Expression *doInline(InlineDoState *ids); @@ -478,7 +478,7 @@ struct AssocArrayLiteralExp : Expression Expression *interpret(InterState *istate, CtfeGoal goal = ctfeNeedRvalue); MATCH implicitConvTo(Type *t); Expression *castTo(Scope *sc, Type *t); - Expression *inferType(Type *t, int flag = 0, TemplateParameters *tparams = NULL); + Expression *inferType(Type *t, int flag = 0, Scope *sc = NULL, TemplateParameters *tparams = NULL); Expression *doInline(InlineDoState *ids); Expression *inlineScan(InlineScanState *iss); @@ -683,7 +683,7 @@ struct FuncExp : Expression Expression *implicitCastTo(Scope *sc, Type *t); MATCH implicitConvTo(Type *t); Expression *castTo(Scope *sc, Type *t); - Expression *inferType(Type *t, int flag = 0, TemplateParameters *tparams = NULL); + Expression *inferType(Type *t, int flag = 0, Scope *sc = NULL, TemplateParameters *tparams = NULL); char *toChars(); void toCBuffer(OutBuffer *buf, HdrGenState *hgs); elem *toElem(IRState *irs); @@ -1656,7 +1656,7 @@ struct CondExp : BinExp void toCBuffer(OutBuffer *buf, HdrGenState *hgs); MATCH implicitConvTo(Type *t); Expression *castTo(Scope *sc, Type *t); - Expression *inferType(Type *t, int flag = 0, TemplateParameters *tparams = NULL); + Expression *inferType(Type *t, int flag = 0, Scope *sc = NULL, TemplateParameters *tparams = NULL); Expression *doInline(InlineDoState *ids); Expression *inlineScan(InlineScanState *iss); diff --git a/src/template.c b/src/template.c index d9e3c6bdabdc..5e4d19e1d48e 100644 --- a/src/template.c +++ b/src/template.c @@ -1499,7 +1499,7 @@ MATCH TemplateDeclaration::deduceFunctionTemplateMatch(Loc loc, Scope *sc, Objec if (farg->op == TOKfunction) { FuncExp *fe = (FuncExp *)farg; Type *tp = prmtype; - Expression *e = fe->inferType(tp, 1, parameters); + Expression *e = fe->inferType(tp, 1, paramscope, inferparams); if (!e) goto Lvarargs; farg = e; @@ -1687,7 +1687,7 @@ MATCH TemplateDeclaration::deduceFunctionTemplateMatch(Loc loc, Scope *sc, Objec { FuncExp *fe = (FuncExp *)arg; Type *tp = tb->nextOf(); - Expression *e = fe->inferType(tp, 1, parameters); + Expression *e = fe->inferType(tp, 1, paramscope, inferparams); if (!e) goto Lnomatch; arg = e; diff --git a/test/compilable/extra-files/ddocYear.html b/test/compilable/extra-files/ddocYear.html index 912269e10279..72343d2cabc7 100644 --- a/test/compilable/extra-files/ddocYear.html +++ b/test/compilable/extra-files/ddocYear.html @@ -1,15 +1,15 @@ -
- -