This is the mail archive of the
mailing list for the GCC project.
ODR violation for std::cout etc.
- From: Michael Veksler <mveksler at tx dot technion dot ac dot il>
- To: gcc at gcc dot gnu dot org
- Date: Tue, 10 Jul 2007 19:44:19 +0300
- Subject: ODR violation for std::cout etc.
Currently libstdc++ violates ODR:
iostream: extern ostream cout;
global_io.cc: fake_ostream cout;
It assumes that gcc will work fine with this. Apparently it does, for now.
After solving a similar problem in my code using a similar technique -
to find out that it does not work for MS VS-2005 - when I had to find a
The question is, why does GCC has to resolve to such construction-order
issue this way?
Idea (which I used):
don't violate ODR in global_io.cc. Instead, construct and destroy
std::cout two times, in a safe way:
static PreSecondCtor coutPreSecondCtor(std::cout);
static PostSecondCtor coutPostSecondCtor(coutPreSecodCtor);
When PreSecondCtor saves all relevant data of cout (error bits, state,
and then calls std::cout.~ostream();
Note that before this point, std::cout has already been constructed by
and we need to avoid double construction.
In PostSecondCtor, restore the state of cout out of the saved data in
During destruction the order is reversed.
I still have a vague feeling that this solution is also undefined (since
we are calling the constructor of std::cout, using placement new, after
it had been automatically destroyed by the C++ environment). I don't
have the standard near me, so I can't check.
Anyway, even if this is undefined, the situation is arguably better
since it does not seem to break whole program compilation (like current
What do you think?