What is WAF? Let’s take a look definition of WAF from wikipedia

web application firewall (or WAF) filters, monitors, and blocks HTTP traffic to and from a web application. A WAF is differentiated from a regular firewall in that a WAF is able to filter the content of specific web applications while regular firewalls serve as a safety gate between servers. By inspecting HTTP traffic, it can prevent attacks stemming from web application security flaws, such as SQL injection, cross-site scripting (XSS), file inclusion, and security misconfigurations.

In short, WAF is a firewall that its purpose is to filter, monitor and block HTTP traffic.

It is very useful to block malicious traffic so that it could not harm web application behind it. It could filters most of attack pattern (if rules is updated regularly).

This time, I will show how to configure mod security firewall in apache webserver using CRS version 3.0.2, and ubuntu server 16.04. And the attact for demo is sql injection.

1. First step, install apache2, php, mysql

apt-get install apache2
apt-get install mysql-server
sudo apt-get install -y php7.0 libapache2-mod-php7.0 php7.0-cli php7.0-common php7.0-mbstring php7.0-gd php7.0-intl php7.0-xml php7.0-mysqlsudo apt-get install -y php7.0 libapache2-mod-php7.0 php7.0-cli php7.0-common php7.0-mbstring php7.0-gd php7.0-intl php7.0-xml php7.0-mysql

2. Next step is create db, table, and php code.

The SQL code

USE sqli; 
CREATE TABLE `fruits` ( `id` int(11) NOT NULL, `name` varchar(50) NOT NULL, `price` int(11) NOT NULL ) ENGINE=InnoDB DEFAULT CHARSET=latin1; 
ALTER TABLE `fruits` ADD UNIQUE KEY `id` (`id`); 
INSERT INTO `fruits` (`id`, `name`, `price`) VALUES (1, 'manggo', 10000), (2, 'apple', 25000);
Create database , table , and insert data
table fruits structure

The PHP code



/*setting connection and db*/
$connect = mysqli_connect("localhost","root","1l0v3y0u","sqli");

/*select & view data*/
$sql = "SELECT * FROM fruits WHERE name='".$_GET["name"]."'";
echo "<b>query executed => </b>".$sql."<hr>";
$query = mysqli_query($connect,$sql);
$data = mysqli_fetch_assoc($query);

<table border=1>
 <td>Fruit Name</td>
 <td><?php echo $data["name"];?></td>
 <td><?php echo $data["price"];?></td>


3. Now access the vulnerable page. Do some sql injection

normal access,
simple injection,’+UNION+SELECT+1,user(),version()–‘ we can get current user that being used to access mysql from php script, also current mysql version
advanced injection,’+/*!50000union*/+/*!50000select*/+1,user(),version()–‘ with some characters to bypass some waf filtering

As we can see, sql injection is executed.

4. Now, install & configure mod security

apt-get install libapache2-modsecurity

Check if mod security was loaded correctly

apachectl -M | grep security


Rename file /etc/modsecurity/modsecurity.conf-recommended into modsecurity.conf

mv /etc/modsecurity/modsecurity.conf-recommended /etc/modsecurity/modsecurity.conf

Download CRS to folder /etc/apache2/modsecurity-crs

git clone https://github.com/SpiderLabs/owasp-modsecurity-crs.git /etc/apache2/modsecurity-crs

Rename file /etc/apache2/modsecurity-crs/crs-setup.conf.example into crs-setup.conf

cd /etc/apache2/modsecurity-crs/ && mv crs-setup.conf.example crs-setup.conf

Update file /etc/apache2/mods-enabled/security2.conf

<IfModule security2_module>
 # Default Debian dir for modsecurity's persistent data
 SecDataDir /var/cache/modsecurity

# Include all the *.conf files in /etc/modsecurity.
 # Keeping your local configuration in that directory
 # will allow for an easy upgrade of THIS file and
 # make your life easier
 IncludeOptional /etc/modsecurity/*.conf
 IncludeOptional /etc/apache2/modsecurity-crs/*.conf
 IncludeOptional /etc/apache2/modsecurity-crs/rules/*.conf

Reload apache

/etc/init.d/apache2 reload

5. Testing for sql injection


As we can see, now mod security blocks any sql injection attempts. And also, other attacks as well, like XSS or directory traversal