TIWAP | Official Walkthrough Part - 1

Difficulty: Hard


TIWAP is a web application designed with an educational purpose for beginners in web application security who desire to learn and explore this field. It focuses on 20 vulnerabilities, each having 3 levels of difficulty.

These vulnerabilities are found on most of the modern web applications which arise due to lack of secure coding practices and common vulnerabilities overlooked by developers.

Initialization

Home Page

Login to the account with the default credentials, i.e. admin:admin and you will enter the user dashboard.

Dashboard Page

As the first step, go to settings and confirm that the difficulty level is set to Hard.

Settings

Now you may start with exploitation.

Exploitation

SQL Injection

Structured Query Language or SQL is a language that is used to perform various operations on relational databases and communicate with the database management systems. These databases contains sensitive information and are highly vulnerable if the SQL statements being passed to them are not properly sanitized. These malicious statements are known as SQL Injection statements that are used to manipulate the database and access confidential information like usernames, passwords, credit card credentials and other personally identifiable information.

In this hard level lab, we need to set our credentials based on the User ID and then perform a login. Such a mechanism is rare but should be considered something you might see in SSO.

SQL Injection-1

Here, I intercepted the request using Bupr Suite, forwaded the same to repeater and modified the ID as follows

1' OR 1=1--
SQL Injection-2

This time, I got a message as "Try Harder" so there is some filtering for the common input. But I think this can be simply passed with the following:

1' OR 2=2--

But it still gave the same message. So I modified the same a bit more.

2' OR 2=2--

Using the payload above, I was able to retrieve all the users.

SQL Injection-3

Now I'll be using the payload below and dump all the hashes.

2' OR 2=2 UNION SELECT username,password from users--
SQL Injection-4

This was possible as there is no input sanitization done at the backend, thus the SQL queries are being executed directly.

Vulnerable code:

# Python3.8 def sqli_hard(usernameid): global dbmanager cur = dbmanager.get_db_connection().cursor() if "1'" in usernameid or "1'OR1=1" in usernameid or "1' OR 1=1" in usernameid or "1' OR '1'='1" in usernameid: return "Try Harder" if "#" in usernameid: usernameid = usernameid.replace("#", "'") try: stmt = "SELECT userid, username FROM users WHERE userid='%s'" % (str(usernameid)) result = cur.execute(stmt) except sqlite3.OperationalError as e: return e return result.fetchall()

Here, you can see that the data is directly being passed to the SQL query resulting in vulnerable queries.

Blind SQL Injection

Blind SQL Injection is similar to SQL Injection, the only difference is that whenever we pass an incorrect query, it does not respond with the error message which we usually get in the standard SQL Injection.

Going back to the previous lab, I passed the userid as demonstrated below and received an error.

2'OR2=2--
Blind SQL Injection-1

Now, if you pass the same input in the Blind SQL Lab there will be no error message.

Blind SQL Injection-2

And if you pass the correct query, you will receive a positive response.

Blind SQL Injection-3

Vulnerable Code:

def blind_sqli_hard(usernameid): global dbmanager cur = dbmanager.get_db_connection().cursor() if "1'" in usernameid or "1'OR1=1" in usernameid or "1' OR 1=1" in usernameid or "1' OR '1'='1" in usernameid: return "Try Harder" if "#" in usernameid: usernameid = usernameid.replace("#", "'") try: stmt = "SELECT userid, username FROM users WHERE userid='%s'" % (str(usernameid)) result = cur.execute(stmt) except sqlite3.OperationalError: return "" return result.fetchall()


NoSQL Injection

The way we have relational databases, we have non-relational databases as well. They are in key-value pair format just like the JSON format, which makes them flexible and easy to manipulate. Although again, they are used to manipulate a database so some malicious inputs can be passed to access the sensitive information being stored.

NoSQL Injection is an uncommon vulnerability, but with increase in usage of NoSQL Databases over SQL Databases, this vulnerability is picking up popularity.

Currently, there is a bug in the lab. Once resolved, this section will be updated.

Command Injection

You must have come across some web applications which have the functionality of checking if a site is up or not. Or for that matter, any such application which performs some system level command in the background.

The input field in these applications could be tricked to read system files or even execute the some system command, resulting in Remote Code Execution. This attack method is known as Command Injection.

In the lab here, we have a Ping tool which sends four ICMP packets to the given IP Address and returns the output as we get in the CLI. Now, the backend command could be like,

ping -c 4 [IP]
Command Injection-1

In the high level difficulty, most of the characters are blocked by the developers hence you cannot use characters like ampersand, pipe, semi-colon, etc. But I tried something different here and it worked.

8.8.8.8 &cat /etc/passwd

I removed the space after the apersand and it worked.

Command Injection-2

This happened because ususally people put a space to differenciate the commands and such a thing could be exploited.

Vulnerable Code:

def cmd_injection_hard(query): filters = ['& ', ';', '|', '-', '$', '(', ')', '`', '||'] for x in filters: if x in query: message = "Input query blocked: " + query return message return cmd_injection_low(query)

Business Logic Flaw

Every web application you use contains an underlying logic which is designed in a way that the application works perfectly for the end user as per the requirements. This logic is the base of how the business of that application works, and is hence referred to as Business logic.

This logic might contain some flaws like default credentials, client side controls, and trusting user behavior, and is therefore called Business Logic Flaws.

In this lab, we need to update the credentials for the user admin, but the given username is "Not-Admin". So, I'll simply intercept the request and try to change the username as "admin"

Business Logic Flaw-1

So, I was able to update the password very easily. This lab does not define a difficulty level instead it teaches us another flaw of Business Logics that the application is not verifying the username.

Vulnerable Code:

elif session['level'] == 2: passwordn = request.form.get('passwordn') result = bl.business_logic_hard(username=username, passwordn=passwordn) return render_template('vulnerabilities/business-logic-hard.html', msg=result) def business_logic_hard(username, passwordn): if dbm.check_user(username=username): if dbm.update_pass(username=username, password=passwordn): return "Password Updated Successfully!!!" return "No user"

Sensitive Data Exposure

An application holds a lot of information which even we are unaware of, although at times the confidential part of that information might be available on the public platform leading to further damage to the application. This leakage of such confidential information is known as Sensitive Data Exposure.

Some most common exposure points of sensitive data are

In this hard level lab, we get the following message on the home page.

Do you know robots leak most of the sensitive data?

So, by mentioning, the application is referring to the robots.txt file. This file is common in most of the applications as it allows Spider and Crawlers to list all the routes in an application.

Sometimes, developers forget to remove some sensitive routes which results in leaking sensitive information.

In this application, the robots.txt file discloses path to a backup file.

Sensitive Data Exposure

But the file isn't accessible when we go to that route. So, I intercepted the request and changed the HTTP request method to POST

POST /backups/card-db.bk HTTP/1.1 Host: 172.17.0.3:5001 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:78.0) Gecko/20100101 Firefox/78.0 Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8 Accept-Language: en-US,en;q=0.5 Accept-Encoding: gzip, deflate Referer: http://172.17.0.3:5001/sensitive-data-exposure Connection: close Cookie: session=.eJwNyU1vgjAYAOC_svS8A6JdItetZVGo0I-XymWplgjyFpnB6Wb87_P2JM-duMvUkuROXnYkIbXFdZ7CtqywcGbM4MilM7cPFdpOxmLUMa4VwJvSfOPMiWYBqAo3VIw_b-R5T1llsQBmIt1Lvo9w2qVtX0Z9rEHWOaPfSstCsv6qQcxdlf9BwJULy7ECr3zKrUgxGEWpjVq3YeVCfPJBRl6AzmduwLMw8L4d6nnNl7_K-gzY2NXobdnNjk1gV_J4Jdj8NEiS-KnT4dD4r24gyXS-NI9_am9QDw.YiBijg.mNtGxFrAm7ZP3mqCwcGp_W-MPvM Upgrade-Insecure-Requests: 1 Cache-Control: max-age=0

Here I got the file named as "card-db.bk"

Vulnerable Code:

@app.route('/backups/card-db.bk', methods=['GET', 'POST']) @is_logged def sensitive_data_exposure_hard(): if request.method == 'POST' and '/sensitive-data-exposure' in request.headers.get('Referer'): return send_from_directory(directory='backups', filename='card-db.bk') else: return redirect(url_for('sensitive_data_exposure'))

XML External Entities (XXE)

In a full stack application, the data can be passed from frontend to backend either in XML format or in JSON format. Both of them have been a part of APIs for a long time now, and to top that, XML is even older than JSON.

If the XML input contains an external reference and the XML parser running at the backend having a weak configuration, could result into disclosure of confidential data by reading internal system files. This attack method is known as XML External Entities or (XXE).

The Lab requires the use of Burp Suite so that we can see how the data is being sent at the backend and the same can be manipulated to read system files.

XXE-1

But here I got nothing. So I made a few changes in the request and modify the following header.

content-type: text/xml

Now the complete request is similar to the medium level so we can pass the following exploit as base64 encoded.

<?xml version="1.0"?> <!DOCTYPE data [ <!ELEMENT data ANY> <!ENTITY file SYSTEM "file:///etc/passwd"> ]> <user><name>&file;</name></user>

And as you can see, I recovered the entire content of file /etc/passwd.

XXE-2

Vulnerable Code:

if session['level'] == 2: if request.headers.get('Content-Type') == 'text/xml': result = xxe.xxe_medium(data=data) def xxe_medium(data): decode_data = base64.b64decode(data) data = unquote(str(decode_data)) if data.startswith("b'") and data.endswith("'"): data = data[2:-1] return xxe_low(data=data)

Security Misconfigurations

Whenever an application is being configured, there are high chances that the administrators might forget or overlook some important configuration options which results in the application to not be able to work properly or become insecure.

Some common misconfigurations are:

This complete application is highly misconfigured; there are no security headers in any web request and you might see many Stack Error messages while working on the application.

© 2024 Simardeep Singh | Some Rights Reserved