disclaimer: this question is about prevention of unintended naming collisions, and make sure the following code fail to compile/link.
[edit] actually I'd be happy with something preventing this to compile/link, or something that solves this, like anonymous namespaces. But anonymous namespaces aren't supposed to go inside headers.
// Class1.h
// --------
namespace SomeLargeLib {
struct S {
int a;
S() { a = 1; }
};
}
// Class1.cpp
// ----------
#include "Class1.h"
void foo() { SomeLargeLib::S s; }
// Class2.h
// --------
namespace SomeLargeLib {
struct S {
int a;
S() { a = 2; }
};
}
// Class2.cpp
// -----------
#include "Class2.h"
int main() {
SomeLargeLib::S s;
return s.a; // returns 1 !!
}
What happens here is that the ctor S::S has two inline definitions, so the linker is allowed to assume all definitions are the same and pick any one. Note that moving the S::S ctors outside of the classes results in a linker error as they are no longer inline.
Anyway, since we shouldn't have anonymous namespaces in headers (see C++ Core Guidelines), what should be done to prevent such ODR violations? A linker error would be perfect but the standard says no diagnostic is needed for ODR violations.