Here limit_bad_template_recursion avoids instantiating foo, and then we
wrongly warn that it isn't defined, because as a non-template (but
templated) friend DECL_TEMPLATE_INSTANTIATION is false.
gcc/cp/ChangeLog:
* decl2.cc (c_parse_final_cleanups): Also check
DECL_FRIEND_PSEUDO_TEMPLATE_INSTANTIATION.
gcc/testsuite/ChangeLog:
* g++.dg/diagnostic/used-inline1.C: New test.
&& !(header_module_p ()
&& (DECL_DEFAULTED_FN (decl) || decl_tls_wrapper_p (decl)))
/* Don't complain if the template was defined. */
- && !(DECL_TEMPLATE_INSTANTIATION (decl)
+ && !((DECL_TEMPLATE_INSTANTIATION (decl)
+ || DECL_FRIEND_PSEUDO_TEMPLATE_INSTANTIATION (decl))
&& DECL_INITIAL (DECL_TEMPLATE_RESULT
(template_for_substitution (decl))))
&& warning_at (DECL_SOURCE_LOCATION (decl), 0,
--- /dev/null
+template <class T> struct A {
+ friend void foo(A*) { } // { dg-bogus "never defined" }
+ void bar() {
+ baz(this); // { dg-error "baz" }
+ foo(this);
+ }
+};
+
+int main()
+{
+ A<int>().bar();
+}