Thứ bảy, ngày 15 tháng 8 năm 2020
Trang chủ Kiến thức cơ bản

Tìm hiểu về Iptables (phần 2)

bài trước, chúng ta đã tìm hiểu về cấu trúc, các table, chain, rule của iptables. Phần này sẽ đưa ra một số ví dụ cụ thể, giúp các bạn hiểu thêm cách sử dụng iptables tạo tường lửa cho server.

1.Chặn các địa chỉ IP

Phổ biến nhất của việc sử dụng tường lửa đó là để chặn các địa chỉ IP.

Ví dụ, bạn muốn chặn IP 59.45.175.62 lạ liên tục gửi những gói tin đến server, bạn sẽ cần chặn toàn bộ các gói tin đến từ địa chỉ IP này.

Chúng ta sẽ thêm 1 rule vào INPUT chain của table filter. Sử dụng lệnh sau:

iptables -t filter -A INPUT -s 59.45.175.62 -j REJECT

Ngoài ra chúng ta cũng hoàn toàn có thể chặn cả dải địa chỉ IP với việc sử dụng CIDR.

iptables -A INPUT -s 59.45.175.0/24 -j REJECT

Tương tự bạn có thể chặn traffic đi tới một IP hoặc 1 dải IP nào đó bằng cách sử dụng OUTPUT chain:

iptables -A OUTPUT -d 31.13.78.35 -j DROP

2.Chèn hoặc thay thế 1 rule vào đúng vị trí

Việc này rất hữu ích trong một số trường hợp, khi bạn cần sắp xếp các rule để vừa có thể chặn các traffic có hại nhưng cũng có thể để cho các traffic phù hợp đến được hệ thống.

Trở lại ví dụ về việc chặn cả dải IP ở phía trên. Khi bạn muốn chặn cả dải IP tấn công server là: 59.45.175.0/24 nhưng lại muốn nhận traffic từ 1 IP duy nhất là 59.45.175.10.

Bởi vì iptables xử lý các rule trong chain one-by-one, nên bạn chỉ cần đơn giản là thêm 1 rule để chấp nhận traffic từ IP 59.45.175.10 bên trên rule chặn dải 59.45.175.0/24 là ok.

iptables -I INPUT 1 -s 59.45.175.10 -j ACCEPT

Rule này sẽ nằm ở dòng đầu tiên, nên gói tin đi vào từ IP 59.45.175.10 sẽ được chấp nhận trước khi gặp rule chặn dải nằm ở dưới:

Chain INPUT (policy ACCEPT)
num target prot opt source destination
1 ACCEPT all -- 59.45.175.10 0.0.0.0/0
2 DROP all -- 59.45.175.0/24 0.0.0.0/0
3 DROP all -- 221.192.0.0/20 0.0.0.0/0
4 DROP all -- 91.197.232.104/29 0.0.0.0/0

3.Giao thức và module

Ngoài việc chặn IP, chúng ta có thể làm nhiều hơn thế với iptables bằng cách sử dụng các module hay bắt các gói tin dựa vào các giao thức.

Ví dụ đơn giản, khi muốn chặn toàn bộ các traffic TCP, bạn chỉ cần chỉ định giao thức TCP trong câu lệnh bằng option -p:

iptables -A INPUT -p tcp -j DROP

Bạn cũng có thể sử dụng với các giao thức khác như: udp hay icmp

Một ví dụ khác hữu ích hơn: chặn truy cập SSH đến server của 1 dải IP,  có thể sử dụng câu lệnh sau:

iptables -A INPUT -p tcp -m tcp --dport 22 -s 59.45.175.0/24 -j DROP

Ở đây sử dụng 2 module tcp với option -m để check port đích SSH là port 22. Nếu muốn chặn cả SSH và VNC của dải IP này, bạn có thể sử dụng 1 mô đun khác của Iptables là multiport:

iptables -A INPUT -p tcp -m multiport --dports 22,5901 -s 59.45.175.0/24 -j DROP

Trong phần tiếp theo, chúng ta sẽ tìm hiểu một module rất quan trọng: module theo dõi kết nối (connection tracking)

4.Connection tracking module:

Nếu thử chặn một địa chỉ IP tại chain INPUT, bạn sẽ nhận thấy một điều rất thú vị, đó là bạn cũng không thể truy cập vào các dịch vụ đặt trên các server có địa chỉ IP đó.

Bạn có thể nghĩ rằng, việc bạn chặn IP đó ở chain INPUT lại có ảnh hưởng đến việc gói tin từ server của bạn đi ra ở chain OUTPUT. Nhưng không phải như vậy. Gói tin của bạn gửi vẫn tới được server có địa chỉ IP bị chặn ở INPUT, nhưng các gói tin server đó gửi trả về thì lại bị server của bạn từ chối.

Để giải quyết vấn đề này, chúng ta cần cho iptables biết không từ chối các gói tin thuộc về các kết nối đang tồn tại. Iptables là tường lửa trạng thái (stateful firewall), nó cung cấp cho chúng ta một module theo dõi kết nối có tên là "conntrack" để giải quyết trường hợp này. Các kết nối được theo dõi bởi module này sẽ có một trong các trạng thái sau:

NEW: trạng thái của một gói tin đầu tiên của 1 kết nối

ESTABLISHED: Trạng thái này được sử dụng cho các gói tin thuộc về các kết nối đã đang tồn tại. Để một kết nối ở trạng thái này, server kết nối cần phải nhận được một gói tin phản hồi từ server khác.

RELATED: Trạng thái này được sử dụng cho các kết nối có liên quan đến các kết nối ESTABLISHED khác. Ví dụ như kết nối truyền dữ liệu của FTP, nó có liên quan đến kết nối điều khiển đã được ESTABLISHED.

INVALID: Trạng thái này có nghĩa là gói tin không có trạng thái phù hợp, có thể do lỗi gì đó xảy ra

UNTRACKED: Các gói tin được xử lý ở RAW table với TARGET NOTRACK sẽ có trạng thái này

DNAT:  là một trạng thái ảo được sử dụng để cho các gói tin mà địa chỉ đích của nó được thay đổi bởi các rules trong NAT table

Trở lại trường hợp trên, chúng ta sẽ cần có một rule sau đặt ở trên đầu tiên để chấp nhận các gói tin thuộc về các kết nối đang tồn tại sẵn:

iptables -A INPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT

Ngoài ra chúng ta có thể loại bỏ các gói tin ở trạng thái INVALID:

iptables -A INPUT -m conntrack --ctstate INVALID -j DROP

Như vậy chúng ta đã biết thêm về việc sử dụng module conntrack với option --ctstate

5.Chặn các gói tin TCP không hợp lệ với module tcp:

Chúng ta sẽ thiết kế một vài rule để chặn các gói tin TCP không hợp lệ.

Module tcp có option --tcp-flags, bạn có thể sử dụng nó để kiểm tra các cờ TCP.

Option --tcp-flags sẽ nhận vào 2 tham số:

Mask: sẽ là các cờ cần được check của gói tin

Compared flags: chọn các cờ được set cho gói tin

Chẳng hạn, bạn muốn chặn các gói tin Sync flood, thì các gói tin với cờ SYN và FIN sẽ không hợp lệ. Khi đó chúng ta có thể loại bỏ các gói tin này bằng rule iptables sau:

iptables -A INPUT -p tcp -m tcp --tcp-flags SYN,FIN SYN,FIN -j DROP

Một trường hợp gói tin không hợp lệ nữa là một kết nối mới không bắt đầu với một gói tin SYN. Như vậy, bạn cần kiểm tra các cờ FIN, RST, ACK và SYN; tuy nhiên chỉ có cờ SYN nên được đặt. Sử dụng kết hợp 2 module mà chúng ta đã biết, ta có rule:

iptables -A INPUT -p tcp -m conntrack --ctstate NEW -m tcp ! --tcp-flags FIN,SYN,RST,ACK SYN -j DROP

Ở trên chúng ta có sử dụng việc phủ định lại một điều kiện với việc sử dụng "!".

Rule trên có nghĩa là: với các gói tin đầu tiên của các kết nối NEW, thực hiện kiểm tra các cờ FIN,SYN,RST,ACK nhưng cờ được đặt cho gói tin phải là SYN, nếu không phải trường hợp này thì loại bỏ toàn bộ do không hợp lệ.

6.Module giới hạn (limit module) - giới hạn gói tin

Trong phần này, chúng ta sẽ tìm hiểu một module khác - module "limit". Chức năng của module này là đặt một giới hạn cho số gói tin có thể gửi tới hệ thống.

Để hiểu module này hoạt động như thế nào, chúng ta sẽ xem xét một ví dụ thực tế tương tự.

Bạn có một hộp với 5 quả bóng. Khi một gói tin đi đến, bạn sẽ phải ném ra một quả bóng. Và bạn sẽ không thể nhận gói tin nữa nếu như hộp không còn bóng. Thêm vào đó, bạn có thể thêm lại bóng vào hộp với tốc độ là 20 phút thêm lại 1 quả. Và theo ngôn ngữ kỹ thuật thì số bóng trong hộp là giá trị "limit-burst" và tốc độ thêm lại bóng vào hộp chính là giá trị "limit"

Bây giờ, giả sử bạn có 10 gói tin đến hệ thống của bạn. Để chấp nhận 5 gói tin đầu tiên, bạn sẽ phải ném ra cả 5 quả bóng trong hộp. Bởi vì trong hộp giờ không còn bóng nên hệ thống sẽ loại bỏ 5 gói tin còn lại. Và bạn sẽ không thể nhận thêm gói tin nào trong vòng 20 phút tới, bởi vì hộp vẫn trống. Sau 45 phút, có 3 gói tin tới hệ thống, lúc này hệ thống sẽ lại chỉ chấp nhận được 2 gói tin và loại bỏ đi bớt 1 gói tin.

Dựa vào cơ chế như vậy, chúng ta có thể sử dụng mô đun limit để giới hạn số lượng gói tin đến server trong một số trường hợp, chẳng hạn như bị ddos.

Một rule limit các gói tin ICMP:

iptables -A INPUT -p icmp -m limit --limit 1/sec --limit-burst 1 -j ACCEPT

7.Một vài chú ý về việc sử dụng Iptables:

- Có hai phiên bản của giao thứ IP đó là IPv4 và IPv6. Các giao thức này có những điểm khác nhau và được xử lý khác nhau trong nhân Linux. Vì vậy, iptables cung cấp các lệnh khác nhau cho các giao thức này đó là iptables cho IPv4 và ip6tables cho IPv6. Ngoài ra, các option sử dụng cho hai lệnh này đều giống nhau.

- Với các lệnh của Iptables, chúng ta đều phải thực hiện với quyền root (sử dụng user root hoặc user có quyền sudo)

- iptables-save và iptables-restore:

Lệnh iptables cung cấp phương thức để thêm, sửa, xóa các rules. Tuy nhiên, workflow đó không thực sự đẹp. Đầu tiên, bạn phải liệt kê ra các rule đang có sẫn. Tiếp theo, cần chỉ ra rule mới nào cần thêm vào, và đặt ở vị trí nào cho hợp lý.....

Nhưng không cần mất công như vậy, iptables có hai câu lệnh phụ là: iptables-save và iptables-restore. Hai câu lệnh này sẽ giúp dump toàn bộ các rules từ toàn bộ các chains và đẩy ra thành output có thể là trực tiếp ra màn hình hoặc file text, sau đó restore trực tiếp từ file.

Bạn có thể xuất toàn bộ rule iptables của hệ thống ra 1 file text bình thường:

iptables-save > iptables.rules

Sau đó thực hiện chỉnh sửa file text bình thường với các rule cần thay đổi và áp dụng lại vào hệ thống bằng lệnh:

iptables-restore < iptables.rules

- Bảo vệ các rules khỏi mất đi sau khi reboot server

Một điều đáng chú ý nữa là các rules iptables sẽ tự động mất đi sau khi server khởi động lại. Chính vì vậy các bạn sẽ cần cài thêm một số công cụ bên ngoài để bảo vệ các rule iptables khỏi bị mất đi sau khi server khởi động lại.

Với các server CentOS:

sudo yum install iptables-services

Với các server Debian, Ubuntu:

sudo apt install iptables-persistent

Việc sử dụng các công cụ này sẽ được VCCloud giới thiệu ở một bài viết khác.

Vậy là chúng ta đã biết sử dụng cơ bản Iptables làm tường lửa cho hệ thống. Hy vọng bài viết này sẽ giúp các bạn xây dựng được một hệ thống an toàn và đảm bảo hơn với Iptables.

 >> Tham khảo thêm: Hướng dẫn cài đặt đơn giản SQL Server 2008 R2.