================
@@ -3430,15 +3430,17 @@ bool Sema::SubstDefaultArgument(
     ContextRAII SavedContext(*this, FD);
     std::unique_ptr<LocalInstantiationScope> LIS;
 
-    if (ForCallExpr) {
+    FunctionDecl *PatternFD =
+        ForCallExpr
+            ? FD->getTemplateInstantiationPattern(/*ForDefinition*/ false)
+            : nullptr;
+    if (PatternFD) {
       // When instantiating a default argument due to use in a call expression,
       // an instantiation scope that includes the parameters of the callee is
       // required to satisfy references from the default argument. For example:
       //   template<typename T> void f(T a, int = decltype(a)());
       //   void g() { f(0); }
       LIS = std::make_unique<LocalInstantiationScope>(*this);
-      FunctionDecl *PatternFD = FD->getTemplateInstantiationPattern(
-          /*ForDefinition*/ false);
----------------
mizvekov wrote:

I think the actual problem here is that `getTemplateInstantiationPattern` 
doesn't work for finding the non-defining friend declaration in the class 
template.

This approach of skipping adding the parameters to the instantiation scope 
would only work in the simple case where the default argument definition 
doesn't refer to any of the parameters. The tests added in this PR doesn't 
cover the non-trivial case where it does refer to them.

Moreover, the whole previous approach seems fraught, as each default argument 
definition could appear in a different templated context, so there is not one 
single function template declaration which would serve as a pattern for all 
default arguments.



https://github.com/llvm/llvm-project/pull/113777
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to