How to install WAF mod-security on Raspberry Pi 4 ?

Reading Time: 4 minutes

I installed mod-security which is very famous for WAF in Raspberry Pi 4!

There are other security threats other than antivirus.
I want to make my nextcloud safe.
Are there any measure for web application?

You will find solution about this.

What is WAF?

WAF is an abbreviation of web application firewall which prevents attacks from attackers to attack web applications like a fire wall.

On the other hand, you might have heard “firewall”.
This operates at network layer of the OSI reference model.
It usually has the function allowing and blocking access based on port base rules.
For home servers, you can assume router in your home has firewall function in general.

As you can see, WAF and firewall defend different parts.
Therefore, it is not enough to install either of them. Both are necessary.

Installing mod-security

As usual you can install easily by apt command.
– Package name is mod-security2 because version is 2.x.

pi@raspberrypi:~ $ sudo apt install libapache2-mod-security2

And you need to enable apache module.

pi@raspberrypi:~ $ sudo a2enmod security2
pi@raspberrypi:~ $ sudo systemctl restart apache2

# I can confirm that it has been enabled
pi@raspberrypi:~ $ a2query -m
security2 (enabled by site administrator)

Initially mod-security is disable in configuration file.
Let’s activate it.

# Use modsecurity's recommended configuration files
pi@raspberrypi:~ $ sudo cp /etc/modsecurity/modsecurity.conf-recommended /etc/modsecurity/modsecurity.conf
pi@raspberrypi:~ $ sudo nvim /etc/modsecurity/modsecurity.conf

# Fix /etc/modsecurity/modsecurity.conf as follows
# SecRuleEngine DetectionOnly
SecRuleEngine On

# Restart apache2 when you're done fixing
pi@raspberrypi:~ $ sudo systemctl restart apache2

Now mod-security is ready!
let’s check behavior!

You can see that malicious access is denied!
– URL: http://<IP address>/?union+select

The logs are recorded as follows.
You can see that “Access denied”!

pi@raspberrypi:~ tail -f /var/log/apache2/error.log
[Wed Nov 18 13:13:17.485727 2020] [:error] [pid 20869:tid 2919232544] [client] [client] ModSecurity: Access denied with code 403 (phase 2). Operator GE matched 5 at TX: anomaly_score. [file "/usr/share/modsecurity-crs/rules/REQUEST-949-BLOCKING-EVALUATION.conf"] [line "93"] [id "949110"] [msg "Inbound Anomaly Score Exceeded (Total Score: 8)"] [severity "CRITICAL"] [tag "application-multi"] [tag "language-multi"] [tag "platform-multi"] [tag "attack-generic"] [hostname ""] [uri "/"] [unique_id "X7SfXZW9OgYf2AIHcCQObAAAAAc"]

That’s it for installing mod-security!

But now it operates by using default rule set included mod-security package.
Therefore, there can happen so-called “false positive” pattern matching that is recognized as attack and blocked even if request is not actually attack.
In fact nextcloud does not work when I activated mod-security with default rules.
– I will try which rule exactly affects to nextcloud behavior near the future.

For the time being, I recommend to operate in a test environment(not production) and check your service works fine as before installing/activating mod-security.
Or setting “Detection only mode which does not prevent access” to identify affection to your service is good strategy.

Confliction with nextcloud

In fact mod-security blocks proper access during using nextcloud.
You can see log as follows.

pi@raspberrypi:~ $ tail /var/log/apache2/error.log
[Tue Dec 08 14:18:04.596661 2020] [:error] [pid 25071] [client] [client] ModSecurity: Warning. Match of "within %{tx.allowed_methods}" against "REQUEST_METHOD" required. [file "/usr/share/modsecurity-crs/rules/REQUEST-911-METHOD-ENFORCEMENT.conf"] [line "46"] [id "911100"] [msg "Method is not allowed by policy"] [data "PUT"] [severity "CRITICAL"] [ver "OWASP_CRS/3.1.0"] [tag "application-multi"] [tag "language-multi"] [tag "platform-multi"] [tag "attack-generic"] [tag "OWASP_CRS/POLICY/METHOD_NOT_ALLOWED"] [tag "WASCTC/WASC-15"] [tag "OWASP_TOP_10/A6"] [tag "OWASP_AppSensor/RE1"] [tag "PCI/12.1"] [hostname ""] [uri "/nextcloud/index.php/apps/user_status/heartbeat"] [unique_id "X8@LHDWoYALJA@sakO@q5gAAAAQ"]
[Tue Dec 08 14:18:04.601432 2020] [:error] [pid 25095] [client] [client] ModSecurity: Access denied with code 403 (phase 2). Operator GE matched 5 at TX: anomaly_score. [file "/usr/share/modsecurity-crs/rules/REQUEST-949-BLOCKING-EVALUATION.conf"] [line "93"] [id "949110"] [msg "Inbound Anomaly Score Exceeded (Total Score: 5)"] [severity "CRITICAL"] [tag "application-multi"] [tag "language-multi"] [tag "platform-multi"] [tag "attack-generic"] [hostname ""] [uri "/nextcloud/index.php/apps/user_status/heartbeat"] [unique_id "X8@LHEh6WBypLbI3fh27zQAAAAY"]

Let’s focus what is exact error in such boring log.

Access denied with code 403 (phase 2). Operator GE matched 5 at TX: anomaly_score.

We can guess mod-security blocked with 403 forbidden because anomaly score reached 5.

The cause of getting up anomaly score is here.

Warning. Match of "within %{tx.allowed_methods}" against "REQUEST_METHOD" required.

It seems REQUEST_METHOD from user is out of normal behavior.

allowed_methods consists of GET HEAD POST OPTIONS as you can see here.

pi@raspberrypi:~ $ grep -r allowed_methods /usr/share/modsecurity-crs/
/usr/share/modsecurity-crs/rules/REQUEST-901-INITIALIZATION.conf: setvar:'tx.allowed_methods=GET HEAD POST OPTIONS'"

User accessed with PUT because of source code in nextcloud.
– We can confirm by finding [data “PUT”] in error.log

Certainly PUT itself is generally a dangerous method, so it is better not to use it.
– An attacker could place a malicious file or overwrite an existing file on server.

However, since this PUT is in nextcloud source code, not an attacker’s operation.
And it is safe if we introduce two-factor authentication.
So we can think that the risk of allowing PUT in nextcloud is little.

Let’s allow PUT only accessing nextcloud.
Id: 91100 is the detection rule which checks REQUEST_METHOD.

pi@raspberrypi:~ $ sudo vim /etc/modsecurity/nextcloud.conf

# Contents of nextcloud.conf below
<Directory ar/www/html/nextcloud/="">
    SecRuleRemoveById 911100

# Restart apache2 to reflect settings
pi@raspberrypi:~ $ sudo systemctl restart apache2

It does not matter to change file name “nextcloud.conf” as you like because it is set as follows.

pi@raspberrypi:~ $ sudo cat /etc/apache2/mods-enabled/security2.conf
<IfModule security2_module="">
    IncludeOptional /etc/modsecurity/*.conf

Finally you see no Warnings/Errors!


How was it?

I introduced antivirus(by past post) and WAF.

Next time, I would like to do HTTPS to encapsulate communication data!