PHP 4 Objects Passed by Value (Pre-5 Gotcha)
debt(d5/e3/b3/t7)
Closest to 'specialist tool catches it' (d5). The term's detection_hints list Rector and PHPCS — both are specialist static analysis / code-mod tools rather than the default compiler or standard linter. The code_pattern `=&\s*\$` gives these tools something concrete to flag, but you wouldn't catch it without running them explicitly.
Closest to 'simple parameterised fix' (e3). The quick_fix is 'Remove =& for objects in PHP 5+ code; use clone explicitly when a true copy is needed.' This is a small, targeted change — swap or remove the reference operator across affected call sites — but may touch several places in a legacy file, making it slightly more than a single one-liner (e1) yet still well within one component.
Closest to 'localised tax' (b3). The applies_to scope is PHP 4.0–4.4 / web context only, and the concern is historical — legacy codebases carrying old PHP 4 object-passing patterns. Once corrected (or once the codebase is PHP 5+), the ongoing maintenance cost is minimal. It doesn't shape every future change, so it stays at b3 rather than climbing higher.
Closest to 'serious trap — contradicts how a similar concept works elsewhere' (t7). The misconception field states explicitly: 'PHP always copied objects — PHP 5 changed this.' A competent modern PHP developer assumes objects are passed by handle (reference-like), so reading PHP 4 code that relies on copy-by-value semantics, or vice versa reading PHP 5 code expecting PHP 4 behaviour, produces exactly the wrong mental model. This directly contradicts modern PHP's behaviour, landing it at t7.
TL;DR
Explanation
In PHP 4, $b = $a where $a is an object creates a complete copy. Methods called on $b don't affect $a. In PHP 5+, objects use handle semantics — assignment copies the handle (reference to the object), so $b = $a makes both point to the same object. To get PHP 4 behaviour in PHP 5+, use clone. In PHP 4, developers used =& to pass objects by true reference. Legacy code using =& for objects is a PHP 4 pattern — remove in PHP 5+. The PHP 5 change was so significant it's the primary reason PHP 4 code is incompatible.
Common Misconception
Why It Matters
Common Mistakes
- Using =& for objects in PHP 5+ — unnecessary, creates a reference alias to the handle.
- Not using clone when a true copy is needed in PHP 5+.
- Assuming old PHP 4 code behaves the same in PHP 5 — it often doesn't due to object semantics.
Code Examples
// PHP 4 pattern — unnecessary in PHP 5+:
$obj2 =& $obj1; // Reference to avoid copy
// PHP 4 actual copy issue:
$obj2 = $obj1;
$obj2->value = 'changed'; // Did NOT change $obj1 in PHP 4
// PHP 5+ — same object:
$obj2 = $obj1;
$obj2->value = 'changed'; // Changes $obj1 too!
// True copy in PHP 5+:
$obj2 = clone $obj1;
$obj2->value = 'changed'; // $obj1 unchanged