Introduction to Deserialization Attacks
Identifying a Vulnerability (PHP)
Scenario (HTBank)
Let's imagine that HTBank GmbH asked us to perform a white-box assessment of their newly developed website. They provided us with a URL, the website's source code, and the hint that it is impossible to create accounts with @htbank.com email addresses because these are what administrators use.
Exploring the Site
Browsing to the website, we are greeted with a login screen for which we were given no credentials.
We do notice that there is an option to register a new account. We can verify that attempting to register a user with an @htbank.com email address results in a The email format is invalid error message, so we will register a test account with the credentials [email protected]:pentest and subsequently log in.
Note: The fact that pentest is allowed as a password signifies the lack of a password policy, but this is out of this module's scope.
Once logged in, we are redirected to the home page, which looks to be populated with placeholder text. Perhaps it is still under development. However, we can see a link in the navbar to /settings, which we should take a look at.
On the Settings page, we see that we can update our username, email, password, and profile picture, as well as import and export some settings. First, we can try to update our email to @htbank.com, but this fails again. We will ignore the profile picture upload for now and focus on the Import/Export Settings feature.
Clicking on Export Settings gives us a long string that looks to be Base64-encoded.
Since it is not clear what this string is, we will decode it locally and find out it is a serialized PHP object.
[!bash!]$ echo -n TzoyNDoiQXBwXEhlbHBlcnNcVXNl...SNIP... | base64 -d
O:24:"App\Helpers\UserSettings":4:{s:30:"App\Helpers\UserSettingsName";s:7:"pentest";s:31:"App\Helpers\UserSettingsEmail";s:16:"[email protected]";s:34:"App\Helpers\UserSettingsPassword";s:60:"$2y$10$kPfp572LjEN1HDYrBOoWqezWZcee58HteiIStVvRu6ndWimUqBN7a";s:36:"App\Helpers\UserSettingsProfilePic";s:11:"default.jpg";}
Since this is a white-box test, we should check the source code to see exactly what this function does. Based on the file structure, we can tell that this is a Laravel application. To save us the effort of looking through each file, we can grep for the message we get after exporting our settings:
[!bash!]$ grep 'Exported user settings!' -nr .
./app/Http/Controllers/HTController.php:123: Session::flash('ie-message', 'Exported user settings!');
Inside app/Http/Controllers/HTController.php, we see the following code, which handles the importing and exporting of user details.
...
public function handleSettingsIE(Request $request) {
if (Auth::check()) {
if (isset($request['export'])) {
$user = Auth::user();
$userSettings = new UserSettings($user->name, $user->email, $user->password, $user->profile_pic);
$exportedSettings = base64_encode(serialize($userSettings));
Session::flash('ie-message', 'Exported user settings!');
Session::flash('ie-exported-settings', $exportedSettings);
}
else if (isset($request['import']) && !empty($request['settings'])) {
$userSettings = unserialize(base64_decode($request['settings']));
$user = Auth::user();
$user->name = $userSettings->getName();
$user->email = $userSettings->getEmail();
$user->password = $userSettings->getPassword();
$user->profile_pic = $userSettings->getProfilePic();
$user->save();
Session::flash('ie-message', "Imported settings for '" . $userSettings->getName() . "'");
}
return back();
}
return redirect("/login")->withSuccess('You must be logged in to complete this action');
}
...
Seeing the use of serialize and unserialize confirms that the Base64 string was a serialized PHP object. In this case, the server accepts a serialized UserSettings object (which is defined in app/Helpers/UserSettings.php) and then updates the logged-in user's details according to the deserialized object's values.
There are no filters or checks on the string when it is imported before it is deserialized, so this looks a lot like something we will be able to exploit.
Note: Import and export of settings or progress are very popular, especially in games, so always keep an eye out for these features as they may be vulnerable if not properly secured.
VPN Servers
Warning: Each time you "Switch", your connection keys are regenerated and you must re-download your VPN connection file.
All VM instances associated with the old VPN Server will be terminated when switching to
a new VPN server.
Existing PwnBox instances will automatically switch to the new VPN server.
PROTOCOL
/ 1 spawns left
Questions
Answer the question(s) below to complete this Section and earn cubes!
Click here to spawn the target system!
Target:
Click here to spawn the target system!
Table of Contents
Introduction
Introduction to Serialization Introduction to Deserialization AttacksExploiting PHP Deserialization
Identifying a Vulnerability (PHP) Object Injection (PHP) RCE: Magic Methods RCE: Phar Deserialization Tools of the TradeExploiting Python Deserialization
Identifying a Vulnerability (Python) Object Injection (Python) Remote Code Execution Tools of the TradeDefending against Deserialization Attacks
Patching Deserialization Vulnerabilities Avoiding Deserialization VulnerabilitiesSkills Assessment
Skills Assessment I Skills Assessment IIMy Workstation
OFFLINE
/ 1 spawns left