ModSecurity: Instalasi

From OnnoWiki
Jump to navigation Jump to search

Sumber: https://www.digitalocean.com/community/tutorials/how-to-set-up-mod_security-with-apache-on-debian-ubuntu

Cara Set Up mod_security dengan Apache di Debian / Ubuntu

Mod security adalah Web Application Firewall (WAF) gratis yang bekerja dengan Apache, Nginx dan IIS. Mendukung aturan yang fleksibel untuk melakukan operasi sederhana dan kompleks dan dilengkapi dengan Core Rule Set (CRS) yang memiliki aturan untuk injeksi SQL, cross site scripting scripting, Trojans, agen pengguna yang buruk, session hijacking dan banyak eksploit lainnya. Untuk Apache, ini adalah modul tambahan yang membuatnya mudah untuk menginstal dan mengkonfigurasi.

Dalam rangka untuk menyelesaikan tutorial ini, Anda akan perlu LAMP diinstal pada Andaserver.

Instalasi mod_security

Instalasi ModSecurity

apt-get install libapache2-modsecurity modsecurity-crs

Periksa apakah modul mod_security dimuat.

apachectl -M | grep --color security

Akan keluar

security2_module (shared)

Anda akan melihat modul bernama security2_module (shared) yang menunjukkan bahwa modul dimuat.

Instalasi ModSecurity meliputi file konfigurasi yang disarankan yang harus diganti:

mv /etc/modsecurity/modsecurity.conf{-recommended,}

Reload Apache

service apache2 reload

Cek directory log Apache, akan ada file

ls -l /var/log/apache2/modsec_audit.log
-rw-r----- 1 root root 0 Mar 30 14:07 /var/log/apache2/modsec_audit.log

Konfigurasi mod_security

Apa adanya, ModSecurity tidak melakukan apa-apa karena kebutuhan aturan untuk bekerja. File konfigurasi default diset ke DetectionOnly yang mencatat permintaan sesuai dengan aturan yang cocok dan tidak memblokir apa-apa. Hal ini dapat diubah dengan mengedit file modsecurity.conf:

nano /etc/modsecurity/modsecurity.conf

Temukan kalimat ini

SecRuleEngine DetectionOnly

Ubah menjadi

SecRuleEngine On

Jika Anda mencoba ini pada server produksi, ubah direktif ini hanya setelah menguji semua aturan Anda.

Direktif lain yang perlu dimodifikasi adalah SecResponseBodyAccess. Ini mengkonfigurasi apakah tubuh respon dibuffered (yaitu dibaca oleh ModSecurity). Ini hanya diperlukan jika deteksi kebocoran data dan perlindungan diperlukan. Oleh karena itu, membiarkannya On akan menggunakan sumber daya droplet dan juga meningkatkan ukuran logfile.

Temukan

SecResponseBodyAccess On

Ubah menjadi

SecResponseBodyAccess Off

Sekarang kita akan membatasi data maksimum yang dapat diposting ke aplikasi web Anda. Dua parameter yang mengkonfigurasi ini:

SecRequestBodyLimit
SecRequestBodyNoFilesLimit

Parameter SecRequestBodyLimit menentukan ukuran data POST maksimal. Jika ada yang lebih besar dikirim oleh client maka server akan merespon dengan error 413 Request Entity Too Large. Jika aplikasi web Anda tidak memiliki file upload nilai ini dapat sangat dikurangi.

Nilai yang disebutkan dalam file konfigurasi

SecRequestBodyLimit 13107200

yaitu 12.5MB.

Sama dengan cara di atas adalah parameter SecRequestBodyNoFilesLimit . Perbedaan terutama pada besarnya data yang di POST dikurangi file uploads -- nilai ini sebaiknya "sekecil-kecilnya yang memungkinkan".

Nilai yang disebutkan dalam file konfigurasi

SecRequestBodyNoFilesLimit 131072

yaitu 128KB.

Diantara parameter-parameter diatas, parameter yang mungkin akan sangat mempengaruhi performance adalah SecRequestBodyInMemoryLimit. Parameter ini menentukan berapa banyak "request body" data (POST data) yang akan di simpan di RAM, selebihnya akan di simpan di harddisk (seperti swap). Jika kita menggunakan SSD, maka hal ini bukan sebuah masalah besar. Kita dapat menset lebih besar jika kita mempunyai RAM lebih,

SecRequestBodyInMemoryLimit 131072

Nilai ini 128KB seperti yang di set di file konfigurasi.

Testing SQL Injection

Sebelum melanjutkan dengan konfigurasi aturan, kita akan membuat script PHP yang rentan terhadap injeksi SQL dan mencobanya. Harap dicatat bahwa ini hanyalah sebuah script PHP untuk login tanpa penanganan sesi. Pastikan untuk mengganti password MySQL di script di bawah ini sehingga akan terhubung ke database:

/var/www/html/login.php

Jika password root MySQL adalah 123456, maka isinya

<html>
<body>
<?php
    if(isset($_POST['login']))
    {
        $username = $_POST['username'];
        $password = $_POST['password'];
        $con = mysqli_connect('localhost','root','123456','sample');
        $result = mysqli_query($con, "SELECT * FROM `users` WHERE username='$username' AND password='$password'");
        if(mysqli_num_rows($result) == 0)
            echo 'Invalid username or password';
        else
            echo 'Logged in - A Secret for you....';
    }
    else
    {
?>
        <form action="" method="post">
            Username: <input type="text" name="username"/>
Password: <input type="password" name="password"/>
<input type="submit" name="login" value="Login"/> </form> <?php } ?> </body> </html>


Script ini akan menampilkan form login. Dengan memasukan password yang tepat akan menampilkan pesan "A Secret for you."

Kita perlu password dalam database. Buat database MySQL dan table, kemudian masukkan username dan password.

mysql -u root -p123456
create database sample;
connect sample;
create table users(username VARCHAR(100),password VARCHAR(100));
insert into users values('jesin','pwd');
insert into users values('alice','secret');
quit;

Buka browser, masuk ke

http://ip-address-web-anda/login.php

misalnya

http://192.168.0.100/login.php

dan masukan pasangan kredensial

Username: jesin
Password: pwd

Kita akan melihat message yang mengindikasikan login sukses. Coba lagi, tapi masukan pasangan kredential yang salah -- kita akan melihat message

Invalid username or password 


Langkah selanjutnya, kita dapat mencba SQL injection untuk mem-bypass login page. Masukan perintah berikut di username:

' or true -- 

Perhatikan ada "spasi" sesudah -- , jika "spasi" tidak di tambahkan sesudah -- maka SQL injection ini tidak akan jalan. Biarkan password kosong. Tekan tombol login.

Simsalabim! script akan memperlihatkan semua message yang harusnya untuk user yang terauthentikasi!


Set Up Rules / Aturan

Untuk membuat hidup kita lebih mudah, akan banyak aturan yang di install bersama dengan mod_security. Hal ini di sebut CRS (Core Rule Set) dan lokasinya di

ls -l /usr/share/modsecurity-crs/
total 44
drwxr-xr-x 2 root root  4096 Mar 31 06:15 activated_rules
drwxr-xr-x 2 root root  4096 Mar 31 06:15 base_rules
drwxr-xr-x 2 root root  4096 Mar 31 06:15 experimental_rules
drwxr-xr-x 2 root root  4096 Mar 31 06:15 lua
-rw-r--r-- 1 root root 13774 Jul 13  2013 modsecurity_crs_10_setup.conf
drwxr-xr-x 2 root root  4096 Mar 31 06:15 optional_rules
drwxr-xr-x 2 root root  4096 Mar 31 06:15 slr_rules
drwxr-xr-x 8 root root  4096 Mar 31 06:15 util

Dokumen tersedia di

ls -l /usr/share/doc/modsecurity-crs/
total 16
-rw-r--r-- 1 root root  623 Jul 12  2013 changelog.Debian.gz
-rw-r--r-- 1 root root 1297 Jul  2  2012 copyright
-rw-r--r-- 1 root root 1138 Mar 16  2012 README.Debian
-rw-r--r-- 1 root root 1485 Jul  2  2013 README.md


Untuk me-load aturan / rules ini, kita perlu memberitahukan Apache untuk melihat directory tersebut. Edit file mod-security.conf

vi /etc/apache2/mods-enabled/security2.conf

Tambahkan aturan berikut di dalam <IfModule security2_module> </IfModule>:

Include "/usr/share/modsecurity-crs/*.conf"
Include "/usr/share/modsecurity-crs/activated_rules/*.conf"

Directory activated_rules sama dengan directory mods-enabled pada Apache. Rules / Aturan yang ada tersedia di directory:

/usr/share/modsecurity-crs/base_rules
/usr/share/modsecurity-crs/optional_rules
/usr/share/modsecurity-crs/experimental_rules

Kita perlu membuat symlinks di dalam directory activated_rules untuk mengaktifkan aturan tersebut.

Contoh, untuk mengaktifkan rules / aturan SQL injection.

cd /usr/share/modsecurity-crs/activated_rules/
ln -s /usr/share/modsecurity-crs/base_rules/modsecurity_crs_41_sql_injection_attacks.conf .

Apache harus di reload agar rules beroperasi / berefek.

service apache2 reload

Now open the login page we created earlier and try using the SQL injection query on the username field. If you had changed the SecRuleEngine directive to On, you'll see a 403 Forbidden error. If it was left to the DetectionOnly option, the injection will be successful but the attempt would be logged in the modsec_audit.log file. Writing Your Own mod_security Rules

In this section, we'll create a rule chain which blocks the request if certain "spammy" words are entered in a HTML form. First, we'll create a PHP script which gets the input from a textbox and displays it back to the user.

/var/www/form.php
<html>
    <body>
        <?php
            if(isset($_POST['data']))
                echo $_POST['data'];
            else
            {
        ?>
                <form method="post" action="">
                        Enter something here:<textarea name="data"></textarea>
                        <input type="submit"/>
                </form>
        <?php
            }
        ?>
    </body>
</html>

Custom rules can be added to any of the configuration files or placed in modsecurity directories. We'll place our rules in a separate new file.

nano /etc/modsecurity/modsecurity_custom_rules.conf

Add the following to this file:

SecRule REQUEST_FILENAME "form.php" "id:'400001',chain,deny,log,msg:'Spam detected'"
SecRule REQUEST_METHOD "POST" chain
SecRule REQUEST_BODY "@rx (?i:(pills|insurance|rolex))"

Save the file and reload Apache. Open http://yourwebsite.com/form.php in the browser and enter text containing any of these words: pills, insurance, rolex.

You'll either see a 403 page and a log entry or only a log entry based on SecRuleEngine setting. The syntax for SecRule is

SecRule VARIABLES OPERATOR [ACTIONS]

Here we used the chain action to match variables REQUEST_FILENAME with form.php, REQUEST_METHOD with POST and REQUEST_BODY with the regular expression (@rx) string (pills|insurance|rolex). The ?i: does a case insensitive match. On a successful match of all these three rules, the ACTION is to deny and log with the msg "Spam detected." The chain action simulates the logical AND to match all the three rules.

Excluding Hosts and Directories

Sometimes it makes sense to exclude a particular directory or a domain name if it is running an application like phpMyAdmin as modsecurity and will block SQL queries. It is also better to exclude admin backends of CMS applications like WordPress.

To disable modsecurity for a complete VirtualHost place the following

<IfModule security2_module>
    SecRuleEngine Off
</IfModule>

inside the <VirtualHost> section.

For a particular directory:

<Directory "/var/www/wp-admin">
    <IfModule security2_module>
        SecRuleEngine Off
    </IfModule>
</Directory>

If you don't want to completely disable modsecurity, use the SecRuleRemoveById directive to remove a particular rule or rule chain by specifying its ID.

<LocationMatch "/wp-admin/update.php">
    <IfModule security2_module>
        SecRuleRemoveById 981173
    </IfModule>
</LocationMatch>



Referensi