http://gcc.gnu.org/bugzilla/show_bug.cgi?id=34434
Andrew Pinski <pinskia at gcc dot gnu.org> changed: What |Removed |Added ---------------------------------------------------------------------------- Status|UNCONFIRMED |RESOLVED Known to work| |4.3.5 Host|x86_64-linux-gnu | Resolution| |FIXED Target Milestone|--- |4.3.5 Build|x86_64-linux-gnu | --- Comment #2 from Andrew Pinski <pinskia at gcc dot gnu.org> 2012-01-28 03:53:51 UTC --- Fixed in 4.3.5. Reduced testcase: typedef unsigned long Word_t; typedef struct struct_vproc VProc_t; struct struct_vproc { unsigned long globNextW; unsigned long globLimit; }; void GetChunkForVProc (); static inline Word_t CompareAndSwapWord (Word_t *ptr, Word_t old, Word_t new) { register Word_t result __asm__ ("%rax"); __asm__ __volatile__ ( "movq %2,%%rbx\n\t": "=m" (*ptr): "g" (old), "g" (new): "memory", "%rax"); return result; } void StartGlobalGC (VProc_t *vp, unsigned long **scanPtr, Word_t *scanTop) { GetChunkForVProc (0); do { Word_t hdr = *scanPtr++; if (isMixedHdr(hdr)) { int len = GetVectorLen(hdr); for (int i = 0; i < len; i++, scanPtr++) { Word_t *v = *scanPtr; if (isPtr(v)&& AddrToChunk() == 0) { Word_t oldHdr = v[-1]; if (isForwardPtr(oldHdr)) { Word_t *nextW = (Word_t *)vp->globNextW; int len = GetLength(oldHdr); if (nextW >= (Word_t *)(vp->globLimit)) nextW = (Word_t *)vp->globNextW; Word_t hdr = CompareAndSwapWord(v-1, oldHdr, nextW); nextW[-1] = hdr; } } } } } while (scanPtr < scanTop); }