From: K dot Londenberg at librics dot de Operating system: Linux 2.6.12-1-386 PHP version: 5.1.2 PHP Bug Type: Scripting Engine problem Bug description: Garbage Collector - bug with circular references.
Description: ------------ The PHP Garbage Collector fails to free objects which are unreachable if they contain circular references to each other. The example script does not provoke an out of memory error, but I have some cases where a script hits the memory limit, even if there are loads of unreachable objects to be finalized. Sorry, but the example code has 32 lines. I guess it won't break your big repository anyway. Compare what happens if you run the example script as it is, and what happens if you uncomment the line containing "$bigd->subdata->subdata = $bigd;" If you want to test this script in a PHP Engine without large memory limits, just lower the numbers. BTW - this is a real problem and does happen quite frequently. All you need is some kind of circular reference between some objects, and everything referenced by those objects won't be cleared by the Garbage Collector until script termination. Reproduce code: --------------- <?php // This Test case demonstrates a bug where the PHP Garbage Collector fails // to release objects which are unreachable but contain circular references. class bigdata { private $data; public $subdata; public function __construct($entries) { $this->data = array(); echo "Creating BIGDATA with $entries entries\n"; if ($entries>=1000) { $this->subdata = new bigdata($entries/2); } for ($i=0;$i<$entries;$i++) { $this->data[] = $i; } } public function __destruct() { echo "Destroyed BIGDATA with ".count($this->data)." entries\n"; } } echo "<PRE>"; echo "Creating bigdata\n";flush(); $bigd = new bigdata(1000); echo "Removing reference to bigdata\n";flush(); $bigd = null; echo "Creating new bigdata\n";flush(); $bigd = new bigdata(1000); echo "Creating circular reference. \n";flush(); //$bigd->subdata->subdata = $bigd; // If you omit this statement, the Gargabe collector will destroy everything as it should. echo "Removing all global references to bigdata\n";flush(); $bigd = null; echo "Now, exiting\n";flush(); exit; ?> Expected result: ---------------- <PRE>Creating bigdata Creating BIGDATA with 1000 entries Creating BIGDATA with 500 entries Removing reference to bigdata Destroyed BIGDATA with 1000 entries Destroyed BIGDATA with 500 entries Creating new bigdata Creating BIGDATA with 1000 entries Creating BIGDATA with 500 entries Creating circular reference. Removing all global references to bigdata Destroyed BIGDATA with 1000 entries Destroyed BIGDATA with 500 entries Now, exiting Actual result: -------------- <PRE>Creating bigdata Creating BIGDATA with 1000 entries Creating BIGDATA with 500 entries Removing reference to bigdata Destroyed BIGDATA with 1000 entries Destroyed BIGDATA with 500 entries Creating new bigdata Creating BIGDATA with 1000 entries Creating BIGDATA with 500 entries Creating circular reference. Removing all global references to bigdata Now, exiting Destroyed BIGDATA with 1000 entries Destroyed BIGDATA with 500 entries -- Edit bug report at http://bugs.php.net/?id=36482&edit=1 -- Try a CVS snapshot (PHP 4.4): http://bugs.php.net/fix.php?id=36482&r=trysnapshot44 Try a CVS snapshot (PHP 5.1): http://bugs.php.net/fix.php?id=36482&r=trysnapshot51 Try a CVS snapshot (PHP 6.0): http://bugs.php.net/fix.php?id=36482&r=trysnapshot60 Fixed in CVS: http://bugs.php.net/fix.php?id=36482&r=fixedcvs Fixed in release: http://bugs.php.net/fix.php?id=36482&r=alreadyfixed Need backtrace: http://bugs.php.net/fix.php?id=36482&r=needtrace Need Reproduce Script: http://bugs.php.net/fix.php?id=36482&r=needscript Try newer version: http://bugs.php.net/fix.php?id=36482&r=oldversion Not developer issue: http://bugs.php.net/fix.php?id=36482&r=support Expected behavior: http://bugs.php.net/fix.php?id=36482&r=notwrong Not enough info: http://bugs.php.net/fix.php?id=36482&r=notenoughinfo Submitted twice: http://bugs.php.net/fix.php?id=36482&r=submittedtwice register_globals: http://bugs.php.net/fix.php?id=36482&r=globals PHP 3 support discontinued: http://bugs.php.net/fix.php?id=36482&r=php3 Daylight Savings: http://bugs.php.net/fix.php?id=36482&r=dst IIS Stability: http://bugs.php.net/fix.php?id=36482&r=isapi Install GNU Sed: http://bugs.php.net/fix.php?id=36482&r=gnused Floating point limitations: http://bugs.php.net/fix.php?id=36482&r=float No Zend Extensions: http://bugs.php.net/fix.php?id=36482&r=nozend MySQL Configuration Error: http://bugs.php.net/fix.php?id=36482&r=mysqlcfg