A local class in C++ can have friend functions, but these functions cannot be defined neither inside the class [class.friend] p5:
A function may be defined in a friend declaration of a class if and only if the class is a non-local class and the function name is unqualified.
nor inside the enclosing function [dcl.fct.def.general] p2:
[...] A function shall be defined only in namespace or class scope. [...]
And what if a friend function of a local class is defined in the global scope as follows:
auto foo() {
struct A;
void bar(const A&);
struct A {
friend void bar(const A&);
};
bar(A{});
return A{};
}
using A = decltype(foo());
void bar(const A&) {}
int main() {
foo();
}
Compilers diverge here:
- MSVC shows a compilation warning and fails during linking:
warning C5046: 'bar': Symbol involving type with internal linkage not defined
error LNK2019: unresolved external symbol "void __cdecl bar(struct `__cdecl foo(void)'::`2'::A const &)" (?bar@@YAXAEBUA@?1??foo@@YA@XZ@@Z) referenced in function "__cdecl foo(void)" (?foo@@YA@XZ)
- EDG shows compilation error:
error: function "bar", declared using a local type, must be defined in this translation unit
- GCC already accepts the program, but only with
-fpermissiveflag, printing the warning:
warning: 'void bar(const foo()::A&)', declared using local type 'const foo()::A', is used but never defined [-fpermissive]
- and only Clang permits this program just fine without single warning: online demo.
Which implementation is correct here?
::to explicitly use the global namespace scope? As infriend void ::bar(const A&);