This is the mail archive of the
gcc@gcc.gnu.org
mailing list for the GCC project.
C++ aliasing problem (noticed with -O2 -march=athlon)
- From: Jakub Bogusz <qboosh at pld dot org dot pl>
- To: gcc at gcc dot gnu dot org
- Date: Mon, 9 Dec 2002 21:55:17 +0100
- Subject: C++ aliasing problem (noticed with -O2 -march=athlon)
I have a question related to C++ aliasing rules - because I'm not sure
what's wrong - some program code or aliasing rules in gcc.
Some library+program (djvulibre) compiled by gcc 3.2 (3.2.1 too)
with "-O2 -march=athlon" segfaults. With other optimizations
(e.g. "-O1 -march=athlon", "-O2 -march=i686" etc.) it doesn't happen.
Also "-O2 -march=athlon -fno-strict-aliasing" optimization generates
good, working code (that's why I suppose it's aliasing-related problem
and athlon is only coincidence).
Offending djvulibre code is (declaration):
#v+
class GPBufferBase
{
public:
GPBufferBase(void *&,const size_t n,const size_t t);
private:
void *&ptr;
};
inline
GPBufferBase::GPBufferBase(void *&xptr,const size_t n,const size_t t) : ptr(xptr), num(n)
{
xptr=(n*t)?(::operator new(n*t)):0;
}
template<class TYPE>
class GPBuffer : public GPBufferBase
{
public:
GPBuffer(TYPE *&xptr,const size_t n=0) : GPBufferBase((void *&)xptr,n,sizeof(TYPE)) {}
}
#v-
...and then use:
#v+
unsigned int *posn;
GPBuffer<unsigned int> gposn(posn,blocksize);
memset(posn, 0, sizeof(unsigned int)*size);
#v-
Good x86 code, generated with e.g. "-O2 -march=i686" or
"-O2 -march=athlon -fno-sctrict-aliasing":
#v+
leal 60(%esp),%esi
[...]
.Lxxx
movl %eax,(%esi)
leal 0(,%edx,4),%ecx
movl 60(%esp),%edi
#v-
Wrong code, generated with "-O2 -march=athlon":
#v+
leal 60(%esp),%esi
[...]
.Lxxx
movl 60(%esp),%edi
leal 0(,%edx,4),%ecx
movl %eax,(%esi)
#v-
"void*" should be valid alias for "unsigned int*", so
isn't "void*&" vs "unsigned int*&" case similar?
TIA
--
Jakub Bogusz http://www.cs.net.pl/~qboosh/
PLD Linux http://www.pld.org.pl/