Use HTTP Headers to defend against WEB attacks (Part1)
We often see various attack methods such as Xss, clickjacking, and session hijacking. In this series of articles, we will introduce various HTTP headers that can be used to defend against common Web attacks and demonstrate their implementation methods through a PHP instance. This series of articles aims to give developers a prompt on how to use HTTP headers to defend against some attacks.
Build a test environment
Data and experiment environment at the end of the article!
You can set the PHP-MYSQL application under XAMPP, WAMP, LAMP, MAMP, of course, this choice depends entirely on your preferences.
In this experiment, I used an Apple Mac machine with MAMP. I put all the files in the "sample" folder under the root directory.
Application features
After setting this lab sample, open the Home Page
Http: // localhost/sample/index. php
We can see that this page is a simple logon page, which performs basic server verification.
The user input field cannot be blank. To complete this function, you only need to use the empty () function of PHP. Therefore, if you do not enter something and click log on, the following page will be returned.
If the entered username and password do not match, the following page will be returned. Of course, to complete this step, you need to perform the database query operation.
The entered user password is correct. The homepage shows that the user has logged on.
This is done using the MySQLi preparation statement, as shown below.
$stmt = $mysqli->prepare("select * from admin where username=? and password=?");$stmt->bind_param("ss",$username,$password);$stmt->execute(); username: adminpassword: 1q2w3e4r5t
Note: In this example, the given password is stored in the database using the SHA1 algorithm. This password can be easily obtained using an online tool.
After logging in, you will see a form that contains a simple Xss vulnerability.
Now we are capturing packets. When logging on, observe the default Header information.
After successfully logging on, we will see a search box where users are allowed to input and return relevant information to users.
The code for building the logon page is as follows:
<?phpsession_start();session_regenerate_id();if(!isset($_SESSION['admin_loggedin'])){ header('Location: index.php');} if(isset($_GET['search'])){ if(!empty($_GET['search'])) { $text = $_GET['search']; } else { $text = "No text Entered"; }}?><!DOCTYPE html>
Use the X-Frame-Options response header to defend against click hijacking
First, we will discuss how to use X-Frame-Options to mitigate click hijacking.
Generally, attackers embed the iframe tag on the vulnerability page to perform click hijacking.
In this experiment, an iframe tag is added to the user management page, as described below.
After successful logon, the http: // localhost/sample/home. php page is displayed.
<!DOCTYPE html>
On the same server, I save this page as iframe.html. When the home page is loaded in the browser, the iframe is also loaded.
Although there is a multi-clock solution to defend against this problem, this article discusses the X-Frame-Options Response Header solution.
X-Frame-Options has the following three values.
DENY: indicates that the page cannot be displayed in a frame, and it is not allowed to be nested in pages with the same domain name.
SAMEORIGIN: indicates that the page can be displayed in a frame on the same domain name page.
ALLOW-FROM: indicates that the page can be displayed in the frame of the specified source.
X-Frame-Options: DENY
Let's start with X-Frame-Options: DENY.
Open the home. php file and add the following line.
Header ("X-Frame-Options: DENY ");
The modified code is as follows:
<?phpsession_start();session_regenerate_id(); header("X-Frame-Options: DENY"); if(!isset($_SESSION['admin_loggedin'])){ header('Location: index.php');} if(isset($_GET['search'])){ if(!empty($_GET['search'])) { $text = $_GET['search']; } else { $text = "No text Entered"; }}?><!DOCTYPE html>
Log out from the web page and log on again to observe the HTTP header information
Obtain the following header information:
If you notice that an X-Frame-Options
Now we can reload iframe without any display.
In Chrome's developer mode, let's look at the hidden secrets.
Use developer mode in Firefox
On the firefox iframe.html page, the following error message is displayed on the console.
X-Frame-Options: SAMEORIGIN
The framework may be used. In this case, you can use the SAMEORIGIN value.
Open the home. php file and add the following code:
Header ("X-Frame-Options: sameorigin ");\
The modified code is as follows:
<?phpsession_start();session_regenerate_id(); header("X-Frame-Options: sameorigin"); if(!isset($_SESSION['admin_loggedin'])){ header('Location: index.php');}if(isset($_GET['search'])){ if(!empty($_GET['search'])) { $text = $_GET['search']; } else { $text = "No text Entered"; }}?><!DOCTYPE html>
Log On again after exiting from the web page. Observe the HTTP header information.
Next, let's take a look at their different working principles.
The first step shows the same iframe.html, from which we can see that there is no problem with loading.
I use a virtual machine to open Kali Linux, put the file into it, and then load the URL (http: // localhost/sample/home. php)
When we open the iframe.html file, it cannot be loaded due to cross-origin restrictions.
In the browser error message, you can see
The error information table is clear and cross-origin is not allowed.
X-Frame-Options: ALLOW-FROM http://www.site.com
X-Frame-Options: ALLOW_FROM option, indicating that the page can be displayed in the frame of the specified source. This option is only applicable to IE and Firefox browsers.
First open the home. php file and add the following code:
Header ("X-Frame-Options: ALLOW-FROM http: // localhost ");
The modified code is as follows:
<?phpsession_start();session_regenerate_id();header("X-Frame-Options: ALLOW-FROM http://localhost");if(!isset($_SESSION['admin_loggedin'])){ header('Location: index.php');}if(isset($_GET['search'])){ if(!empty($_GET['search'])) { $text = $_GET['search']; } else { $text = "No text Entered"; }}?><!DOCTYPE html>
Exit the webpage, log on again, and observe the HTTP Header
If we try to load iframe from the same server, no error will occur on the webpage.
This is because the server allows loading the http: // localhost address.
Now let's modify the HTTP header and load it again.
Add
Header ("X-Frame-Options: ALLOW-FROM http://www.androidpentesting.com ");
The modified code is as follows:
<?phpsession_start();session_regenerate_id();header("X-Frame-Options: ALLOW-FROM http://www.androidpentesting.com");if(!isset($_SESSION['admin_loggedin'])){ header('Location: index.php');}if(isset($_GET['search'])){ if(!empty($_GET['search'])) { $text = $_GET['search']; } else { $text = "No text Entered"; }}?><!DOCTYPE html>
The following is the HTTP header information obtained from packet capture:
The previous page is refreshed and the iframe will not be loaded.
The returned error message is as follows:
Obviously, http: // localhost is not licensed.
Summary
This article describes how to use HTTP response headers to prevent Web attacks. In the next article, we will continue to introduce the application of other HTTP Response Headers in Web attacks.