Insecure deserialization
Important: a serialized object may not be obvious at first view. Example:
URL decode
Base64 token decoding
Manipulating serialized objects
You can either edit the object directly in its byte stream form
You can write a short script in the corresponding language to create and serialize the new object yourself
Modifying object attributes
Identify serialized object (here in the cookie)
Decode it
Modify attributes
Re-encode the object and overwrite (the cookie)
Note: This simple scenario is not common in the wild
Modifying data types
PHP -> if you perform a loose comparison ==
between an integer and a string, PHP will attempt to convert the string to an integer, meaning that 5 == "5"
evaluates to true
.
Attacker can modify the password attribute so that it contained the integer 0
-> authentication bypass.
Note:
This is only possible because deserialization preserves the data type.
When modifying data types in any serialized object format, update any type labels and length indicators in the serialized data too (Otherwise, the serialized object will be corrupted and will not be deserialized).
Using application functionality
Consider "Delete user" functionality, the user's profile picture is deleted by accessing the file path in the $user->image_location attribute
If this $user was created from a serialized object, an attacker could exploit this by passing in a modified object with the image_location set to an arbitrary file path
Magic methods
Magic methods are a special type of method that are automatically triggered by specific events or scenarios, without explicit invocation. Developers use them to define code execution for these events (e.g.,
__construct()
). Some languages have magic methods that are invoked automatically during deserialization.In Java deserialization, the
ObjectInputStream.readObject()
method is used to read data from the initial byte stream and essentially acts like a constructor for "re-initializing" a serialized object.
They allow you to pass data from a serialized object into the website's code before the object is fully deserialized.
Injecting arbitrary objects
Deserialization methods often don't validate the objects they process. Attackers can pass any serializable class, allowing them to instantiate arbitrary classes. With source code access, you can:
Identify classes with deserialization magic methods
Check if they perform unsafe operations on controllable data
Then pass in a serialized object of this class to use its magic method for an exploit.
Gadget chains
A "gadget" is a code snippet in an application that helps an attacker achieve a goal, such as invoking a method to pass input into another gadget. Many insecure deserialization vulnerabilities are exploitable through gadget chains.
Identifying gadget chains manually is arduous and nearly impossible without source code access. But if a gadget chain in Java's Apache Commons Collections library is exploitable on one website, other websites using this library may also be vulnerable.
Tools (ysoserial , PHPGGC)
They lets you select a provided gadget chain for a target library, input a command to execute, and generates a serialized object. This reduces the manual effort of crafting gadget chains, though some trial and error is still needed.
Java
PHP
Note:
Pay attention if you need to encode (e.g. URL encode) your payload
A payload might work even if the server returns an error...
Working with documented gadget chains
If no dedicated tool exists for exploiting known gadget chains in the target application's framework, consider searching online for documented exploits to adapt manually.
Last updated