ID: 33595 Comment by: taneli at crasman dot fi Reported By: rodricg at sellingsource dot com Status: Assigned Bug Type: Class/Object related Operating System: * PHP Version: 6CVS-2005-08-02 Assigned To: dmitry New Comment:
It shouldn't be a known "got cha". I just wrote a backgrounded daemon using PHP and I had to instate a checker process just to restart the process any time it dies (because it leaks memory about 30 megs per "daemon loop", because of references). Previous Comments: ------------------------------------------------------------------------ [2006-11-02 22:28:05] judas dot iscariote at gmail dot com taneli at crasman dot fi : - This is a well known "gotcha" see [1] - for the gory details, please see [2], this is not "that easy" to fix. 1. http://en.wikipedia.org/wiki/Reference_counting#Advantages_and_disadvantages 2. ftp://ftp.cs.utexas.edu/pub/garbage/bigsurv.ps ------------------------------------------------------------------------ [2006-11-01 09:07:48] taneli at crasman dot fi Please address this bug, it's very short-sighted to rely on the fact that memory is freed on shutdown (especially when your either your box starts trashing or memory_limit kicks in and fails your request because of a bug in the interpreter). ------------------------------------------------------------------------ [2006-08-15 12:02:00] ruslan dot kyrychuk at gmail dot com Maybe solutution can be to call destructor every time when new object is assigned to old reference? Example: <?php class A { function __construct () { $this->b = new B($this); } function __destruct () { $this->b->__destruct(); } } class B { function __construct ($parent = NULL) { $this->parent = $parent; } function __destruct () { unset($this->parent); } } for ($i = 0 ; $i < 1000000 ; $i++) { $a = new A(); $a->__destruct(); } echo number_format(memory_get_usage()); ?> $a->__destruct(); can be called automatically because new reference is created. Then writing correct destructors will solve this issue. Or maybe I missing something? ------------------------------------------------------------------------ [2006-05-04 14:08:22] frode at coretrek dot com I worked around this exact problem by using a proxy class with a destructor that explicitly breaks the cycle; I got the idea from a perl.com[1] article describing how perl suffers from the same problem. It's also interesting to note that perl has chosen a different (less elegant) solution to the problem than python, by introducing weak references. [1] http://www.perl.com/pub/a/2002/08/07/proxyobject.html ------------------------------------------------------------------------ [2006-04-13 06:24:02] seufert at gmail dot com I have been experiencing this problem. Unfortunately i have an application which relies heavily on a class->driver arrangement where both the class and the driver class need a reference to each other. I was wondering if we could have a way of getting an uncounted reference to the object to pass to the child? So the child would have a reference to the parent, but it would not be counted, and therefore when all external references to the parent are removed/unset, the parent will GC, and then the child will be freed as usual. Is this a workable solution? Even just a reference count decrement would work. Not a perfect solution, but it would solve calling descructors all the time. ------------------------------------------------------------------------ The remainder of the comments for this report are too long. To view the rest of the comments, please view the bug report online at http://bugs.php.net/33595 -- Edit this bug report at http://bugs.php.net/?id=33595&edit=1