[Zope-dev] segfaults in cPersistence under 2.6

Anthony Baxter anthony@interlink.com.au
Fri, 25 Jul 2003 16:02:47 +1000


Wow. I'm having _so_ much fun with 2.6. I'm now seeing a reproducible
segfault on startup. 

Program received signal SIGSEGV, Segmentation fault.
0xfe4517c8 in accessed (self=0xedbe58) at ZODB/cPersistence.c:160
160             self->ring.next->prev = self->ring.prev;
(gdb) p self
$1 = (cPersistentObject *) 0xedbe58
(gdb) p self->ring
$2 = {prev = 0xe5d8fc, next = 0xeb7b210c}
(gdb) p self->ring.prev
$3 = (struct CPersistentRing_struct *) 0xe5d8fc
(gdb) p self->ring.next
$4 = (struct CPersistentRing_struct *) 0xeb7b210c
(gdb) p self->ring.next->prev
Cannot access memory at address 0xeb7b210c.

#0  0xfe4517c8 in accessed (self=0xedbe58) at ZODB/cPersistence.c:160
#1  0xfe4526b4 in Per_getattr (self=0xedbe58, oname=0xbf280, 
    name=0xbf295 "as_key", getattrf=0xfe6d7cec <EC_findiattro>)
    at ZODB/cPersistence.c:524
#2  0xfe452774 in Per_getattro (self=0xedbe58, name=0xbf280)
    at ZODB/cPersistence.c:539
#3  0x64bd8 in PyObject_GetAttr (v=0xedbe58, name=0xbf280)
    at Objects/object.c:1052
#4  0x21c34 in eval_code2 (co=0x8090f8, globals=0x49daac, locals=0x8, 
    args=0xbf280, argcount=2, kws=0x0, kwcount=0, defs=0x0, defcount=0, 
    closure=0x0) at Python/ceval.c:1773
#5  0x245b8 in call_eval_code2 (func=0x80ac24, arg=0xd9230c, kw=0x0)
    at Python/ceval.c:2979
#6  0x24108 in call_object (func=0x80ac24, arg=0xd9230c, kw=0x0)
    at Python/ceval.c:2818
#7  0x23f64 in PyEval_CallObjectWithKeywords (func=0x80ac24, arg=0xd9230c, 
    kw=0x0) at Python/ceval.c:2753
#8  0xfe6d4614 in callMethodWithPossibleHook (inst=0xea55d8, meth=0x80ac24, 
    args=0xd9230c, kw=0x0)

The code in question is here:

    /* Do nothing unless the object is in a cache and not a ghost. */
    if (self->cache && self->state >= 0) {
        CPersistentRing *home = &self->cache->ring_home;
        self->ring.prev->next = self->ring.next;
>>>     self->ring.next->prev = self->ring.prev;
        self->ring.next = home;
        self->ring.prev = home->prev;
        home->prev->next = &self->ring;
        home->prev = &self->ring;
    }

So it seems that the ring's getting corrupted in some way. Any tips on 
tracking this down? I'm thinking of a simple function that just zips
around the ring checking that it's sane in both directions...

(yes, I've confirmed that all the C extensions have been rebuilt cleanly).

--
Anthony Baxter     <anthony@interlink.com.au>
It's never too late to have a happy childhood.