PHP Object Injection
Also Known As
PHP unserialize attack
object injection
PHP deserialization
TL;DR
Passing attacker-controlled data to unserialize() triggers magic methods on existing classes, enabling code execution, file deletion, or SSRF.
Explanation
PHP Object Injection is the practical exploit of insecure deserialization. When unserialize() processes attacker-controlled input, it instantiates arbitrary classes already loaded in the application's autoloader and calls __wakeup(), __destruct(), and __toString() as part of reconstruction. Attackers craft Property Oriented Programming (POP) chains — sequences of magic method calls across multiple classes that together achieve a malicious effect. Tools like PHPGGC (PHP Generic Gadget Chains) automate POP chain generation for popular frameworks. The fix: never unserialize untrusted data.
How It's Exploited
An attacker crafts a serialized payload that, when deserialized, triggers a gadget chain: __destruct() on a file logger class calls unlink() with an attacker-controlled filename, deleting arbitrary files on the server.
Common Misconception
✗ PHP object injection is only dangerous if the codebase has obvious gadget chains. Modern exploit tools automatically scan autoloaded classes for usable magic method chains — large applications with many dependencies almost always have exploitable gadgets.
Why It Matters
PHP's unserialize() invokes magic methods like __wakeup, __destruct, and __toString on attacker-crafted objects — existing classes in the application's autoloader can be chained into arbitrary code execution.
Common Mistakes
- Passing user-controlled cookies, GET/POST parameters, or database values to unserialize().
- Believing that base64 encoding or encryption of serialized data prevents injection — if the key is compromised or the encoding bypassable, it doesn't help.
- Using serialize()/unserialize() for caching or session storage of user-controllable data.
- Not auditing installed packages for gadget chains — popular frameworks have known deserialization gadgets.
Code Examples
✗ Vulnerable
// Deserializing user-controlled data:
$prefs = unserialize(base64_decode($_COOKIE['user_prefs']));
// Attacker crafts a serialized object with __destruct that writes a webshell
✓ Fixed
// Never unserialize user input — use JSON instead:
// Bad:
// $obj = unserialize($_COOKIE['prefs']);
// Safe: JSON for data exchange:
$prefs = json_decode($_COOKIE['prefs'] ?? '{}', true);
if (!is_array($prefs)) $prefs = [];
// If unserialize is absolutely needed, use allowed_classes:
$obj = unserialize($data, ['allowed_classes' => [SafeClass::class]]);
// Only SafeClass can be instantiated — gadget chains blocked
// Verify data integrity with HMAC before deserializing:
$expected = hash_hmac('sha256', $data, SECRET_KEY);
if (!hash_equals($expected, $signature)) {
throw new SecurityException('Data tampered');
}
$obj = unserialize($data, ['allowed_classes' => false]);
References
Tags
🤝 Adopt this term
£79/year · your link shown here
Added
15 Mar 2026
Edited
22 Mar 2026
Views
27
🤖 AI Guestbook educational data only
|
|
Last 30 days
Agents 0
No pings yet today
No pings yesterday
Perplexity 8
Amazonbot 6
Unknown AI 3
Ahrefs 2
Google 1
ChatGPT 1
Also referenced
How they use it
crawler 20
pre-tracking 1
Related categories
⚡
DEV INTEL
Tools & Severity
🔴 Critical
⚙ Fix effort: Medium
⚡ Quick Fix
Replace unserialize() with json_decode() — JSON cannot carry PHP class information so no objects are reconstructed; if you must unserialize, use allowed_classes: [] strictly
📦 Applies To
PHP 5.0+
web
cli
🔗 Prerequisites
🔍 Detection Hints
unserialize() of any user-supplied data; cookie session data stored as serialized PHP objects
Auto-detectable:
✓ Yes
semgrep
psalm
phpstan
⚠ Related Problems
🤖 AI Agent
Confidence: High
False Positives: Medium
✗ Manual fix
Fix: High
Context: File
Tests: Update
CWE-502