How to Avoid Web Security Vulnerabilities
1. Course Introduction
This course offers a hands-on tutorial that includes practical exercises. To enhance understanding of specific actions during the experiments, theoretical content will also be covered. Furthermore, carefully selected articles will be recommended to help build a strong theoretical foundation. The course emphasizes clickjacking prevention to ensure comprehensive learning.
Note: Due to the higher cost of setting up the cloud host used for the experiments, the number of trial attempts is limited to no more than six per experiment.
2. Learning Methodology
The Kali series courses on Experiment Lab include five training camps, with this particular camp focusing on methods for attacking web applications. The course consists of 20 experiments, each containing detailed steps and visual aids. It is specifically designed for individuals with basic Linux system knowledge who want to quickly get started with Kali penetration testing.
The recommended approach is to practice extensively and ask questions frequently. Once the experiment is launched, follow the step-by-step instructions while understanding the details of each step.
If any study materials are recommended at the start of an experiment, be sure to read them thoroughly before proceeding. Theoretical knowledge is the essential foundation for practical applications.
3. Overview of This Section
In this experiment, we will introduce the basics of Kali Linux and penetration testing concepts. The following tasks need to be completed in order:
- An introduction to HTTP Header defenses
- Prevention of Clickjacking
- Avoidance of Cookie Theft
5. HTTP Header Defenses
5.1 Overview
In this experiment, we will discuss various aspects of HTTP Headers.
In previous lessons, we learned about attacks related to HTTP Header injection. In this chapter, we will cover strategies for defending against these vulnerabilities. By enabling certain HTTP Header functionalities during development, we can defend against attacks like web session hijacking and clickjacking vulnerabilities, as well as other attacks, not limited to HTTP Header injections.
5.2 Setting Up the Environment
For this experiment, we will no longer use Kali Linux and DVWA for demonstrations. Instead, we have prepared a small PHP-based environment for you.
Use the command cd /var/www/html/
to navigate to the root directory of the Apache server, and then use the following three commands to download the prepared files:
sudo wget http://labfile.oss.aliyuncs.com/courses/717/iframe.html
sudo wget http://labfile.oss.aliyuncs.com/courses/717/index.php
sudo wget http://labfile.oss.aliyuncs.com/courses/717/search.php
Once downloaded, you can verify the presence of the three files (index.php, iframe.html, search.php) in the Apache root directory by running ls -lah
.
Use sudo service apache2 start
to start the Apache server:
Open Firefox, and in the address bar, type localhost
. If the Apache homepage is displayed, it means the environment is successfully set up:
5.3 Prevention of Clickjacking
After completing all preparations, the first vulnerability weâll address is clickjacking.
Clickjacking is a technique where malicious content (e.g., hidden code) is placed beneath seemingly harmless content (like a button) on a webpage, tricking users into clicking it. This is also known as UI redressing.
For example, a user may receive an email containing a video, but clicking the âPlayâ button actually redirects the user to a shopping site. When the user attempts to play the video, they are deceived into visiting the malicious site instead. (Definition adapted from Wikipedia.)
In simple terms, attackers present a normal-looking webpage, but when the user interacts with it, they fall into a trap. This attack is typically implemented using an iframe to load an interesting webpage, which is then covered by a transparent layer with hidden malicious buttons. Letâs walk through an example.
Let me know if youâd like further refinement!
When we click the login button in the top left corner, we see a popup message like this:
The notification confirms that we have successfully logged in.
At the same time, we visit localhost/iframe.html
. We can see an identical page:
However, when we interact with the page, we notice a different type of popup:
This is called clickjacking. It works by disguising a fake interface as a legitimate one, leading you to believe you are interacting with a trusted website. Instead, this is an attackerâs site. During the attack, your interaction might not trigger a simple popup but instead result in the extraction of your credentials, such as username, password, cookies, and more.
We can inspect the source code of the page to understand the simple mechanism behind this technique:
Itâs achieved using an iframe
tag to load the original page, with an overlaying invisible div
. This div captures your clicks and executes the embedded JavaScript ifsub()
function to display a popup window.
From this example, it becomes evident that the critical factor is using an iframe to mimic a credible page. To prevent such a vulnerability, we need to make it impossible for attackers to load our page within an iframe, which will block this type of exploit entirely.
The solution to this vulnerability is straightforward: we need to include a specific HTTP header in our page:
Use the sudo vim /var/www/html/index.php
command to modify the file. Initially, the code might look like this:
Remove the comment to make the code active:
After saving and exiting with :wq
, access localhost/iframe.html
again. You will notice a blank page because the attacker can no longer embed your page within an iframe. This successfully blocks the clickjacking attack.
X-Frame-Options has three possible values:
- DENY: Prevents the page from being displayed in any frame, even within the same domain.
- SAMEORIGIN: Allows the page to be displayed only in frames that belong to the same origin (domain).
- ALLOW-FROM uri: Permits embedding of the page in a frame, but only from specified origins (reference: MDN Web Docs).
Since we set the header to DENY
, no other page can use an iframe to embed ours.
The header
tag we introduced affects how HTTP headers are managed. But what exactly is a header?
HTTP operates on a request/response model where the client (browser, for example) sends a request, and the server responds. HTTP headers are part of this communicationâthey define parameters for the request or response operation (source: Wikipedia).
5.4 Protect Against Cookie Theft
Developers with some experience might think iframe usage is outdated, and the clickjacking prevention method discussed earlier is less impactful. So letâs dive into cookie protection. In earlier experiments, we demonstrated stealing cookies using reflected XSS to hijack sessions.
How can we prevent our cookies from being stolen by malicious scripts? Consider this example:
On Firefox, navigate to localhost/index.php
to visit a prepared login page. Enter the username: shiyanlou
and password: shiyanlou
.
By logging in, the server creates a session and redirects to the `search.php` page. On this page, we have embedded JavaScript code to obtain cookies. Once redirected, we can see a popup like this:
Reviewing the source code reveals how straightforward this implementation is:
Using the provided login page, PHP retrieves the entered credentials and verifies if the username and password both equal `shiyanlou`. If they match, the system creates a session and redirects to the `search.php` page.
Reviewing the source code of `search.php`, we can see the following:
session_start();
session_regenerate_id();
if (!isset($_SESSION['name'])) {
header('Location: index.php');
}
As long as a session exists, the user will remain on the current page without being redirected back to `index.php`.
Additionally, we execute JavaScript to retrieve the session:
This allows us to obtain the session. Similarly, an attacker could inject JavaScript through reflected or stored XSS attacks to acquire the `sessionid`.
To mitigate this vulnerability, we edit the `search.php` source code using the command sudo vim /var/www/html/search.php
. Find the following in the first line:
#ini_set("session.cookie_httponly", "True");
Remove the comment, so it looks like this:
ini_set("session.cookie_httponly", "True");
Save and exit using :wq
. When we refresh the page after this change, the popup will still appear, but its content will be empty:
The reason JavaScript can no longer access the session is the `httponly` flag.
This flag restricts cookies to being accessed only via HTTP protocols, effectively preventing JavaScript from accessing them. This reduces the risk of session theft through XSS attacks.
11. Summary
In this experiment, we covered the following topics. Feel free to visit Shiyanlou Q&A for clarification on any difficult points:
- Overview of HTTP header-based defenses
- Preventing clickjacking
- Mitigating cookie theft
Make sure to complete the entire experiment hands-on. Simply reading the text is easy, but real challenges arise during practical implementation. Solving these challenges is the real learning experience.