On Thu, 2003-04-03 at 23:37, Tim Peters wrote: > > ! next = gc->gc.gc_next; > > if (has_finalizer(op)) { > > gc_list_remove(gc); > > gc_list_append(gc, finalizers); > > gc->gc.gc_refs = GC_MOVED; > > } > > } > > } > > --- 277,290 ---- > > for (; gc != unreachable; gc=next) { > > PyObject *op = FROM_GC(gc); > > ! /* has_finalizer() may result in arbitrary Python > > ! code being run. */ > > if (has_finalizer(op)) { > > + next = gc->gc.gc_next; > > gc_list_remove(gc); > > gc_list_append(gc, finalizers); > > gc->gc.gc_refs = GC_MOVED; > > } > > + else > > + next = gc->gc.gc_next; > > } > > } > > Are we certain that has_finalizer() can't unlink gc itself from the > unreachable list? If it can, then > > > + else > > + next = gc->gc.gc_next; > > will set next to the content of free()ed memory. In fact, I believe the > Boom program will suffer this fate ... yup, it does. "The problem" isn't > yet really fixed in any version of Python, although I agree it's a lot > better with the change above. It looks like it's hard to find a place to stand. Since arbitrary Python code can run, then an arbitrary set of objects in the unreachable list can suddenly become unlinked. The previous, current, and next objects are all suspect. I think a safe approach would be to move everything out of unreachable and into either "collectable" or "finalizers". That way, we can do a while (!gc_list_is_empty(unreachable)) loop and always deal with the head of the unreachable list. Each time through the loop, the head of the list can be moved to collectable or finalizers or become unlinked, so we always make progress. Sound plausible? Jeremy
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4