Firewalls (Tường lửa) là công cụ quan trọng có thể được cấu hình nhằm bảo vệ máy chủ và cơ sở hạ tầng của bạn. Trong hệ sinh thái Linux, iptables là một công cụ tường lửa được sử dụng rộng rãi, hoạt động cùng với khung lọc gói tin netfilter của nhân hệ thống. Việc xây dựng các chính sách tường lửa đáng tin cậy có thể gặp nhiều thách thức do cú pháp phức tạp và số lượng các thành phần liên quan.
IPTables và Netfilter là gì?
Trong nhiều năm qua, phần mềm tường lửa phổ biến nhất trên Linux được gọi là iptables. Ở một số bản phân phối, nó đã được thay thế bởi công cụ mới có tên nftables, nhưng cú pháp của iptables vẫn được dùng làm cơ sở. Tường lửa iptables hoạt động bằng cách tương tác với các điểm cắm (hook) lọc gói tin trong ngăn xếp mạng của nhân Linux – những điểm cắm này được gọi là khung netfilter.
Mỗi gói tin đi qua lớp mạng (dù là đến hay đi) sẽ kích hoạt các điểm cắm này, cho phép các chương trình can thiệp vào lưu lượng tại các điểm then chốt. Các module của nhân liên quan đến iptables sẽ đăng ký với những điểm cắm đó nhằm đảm bảo lưu lượng tuân thủ các điều kiện được quy định bởi các quy tắc tường lửa.
Netfilter Hooks
Có năm điểm cắm (netfilter hooks) mà các chương trình có thể đăng ký. Khi gói tin di chuyển qua ngăn xếp, chúng sẽ kích hoạt các module của nhân đã đăng ký với các hook này. Hook nào được kích hoạt cho một gói tin phụ thuộc vào việc gói tin đó đến hay đi, đích đến của nó, cũng như việc gói tin đã bị loại bỏ hay từ chối ở một điểm nào đó trước đó.
Các hook dưới đây đánh dấu những điểm cụ thể trong ngăn xếp mạng:
NF_IP_PRE_ROUTING
: Điểm cắm này được kích hoạt bởi bất kỳ lưu lượng đến nào ngay sau khi bước vào ngăn xếp mạng. Nó được xử lý trước khi có bất kỳ quyết định định tuyến nào về nơi gửi gói tin.NF_IP_LOCAL_IN
: Điểm cắm này được kích hoạt sau khi một gói tin đến đã được định tuyến, nếu gói tin đó dành cho hệ thống cục bộ.NF_IP_FORWARD
: Điểm cắm này được kích hoạt sau khi một gói tin đến đã được định tuyến, nếu gói tin sẽ được chuyển tiếp đến máy chủ khác.NF_IP_LOCAL_OUT
: Điểm cắm này được kích hoạt bởi bất kỳ lưu lượng đi nào được tạo ra cục bộ ngay khi nó chạm vào ngăn xếp mạng.NF_IP_POST_ROUTING
: Điểm cắm này được kích hoạt bởi bất kỳ lưu lượng đi hoặc chuyển tiếp nào sau khi định tuyến đã được thực hiện và ngay trước khi gói tin được gửi ra ngoài.
Các module của nhân cần đăng ký tại những hook này cũng phải cung cấp một số ưu tiên (priority) để xác định thứ tự gọi khi hook được kích hoạt. Điều này tạo điều kiện cho nhiều module (hoặc nhiều phiên bản của cùng một module) được kết nối với các hook theo một thứ tự nhất định. Mỗi module sẽ được gọi lần lượt và trả về một quyết định cho khung netfilter, chỉ ra hành động cần thực hiện đối với gói tin.
Các Bảng và Chuỗi trong IPTables
Tường lửa iptables sử dụng các bảng để tổ chức các quy tắc của nó. Các bảng này phân loại quy tắc theo loại quyết định mà chúng được sử dụng để đưa ra. Ví dụ, nếu một quy tắc liên quan đến chuyển đổi địa chỉ mạng (network address translation), nó sẽ được đặt vào bảng nat. Nếu quy tắc nhằm quyết định có cho phép gói tin tiếp tục đến đích hay không, nó có thể được thêm vào bảng filter.
Bên trong mỗi bảng, các quy tắc lại được tổ chức thành các chuỗi riêng biệt. Trong khi bảng được định nghĩa theo mục tiêu chung của các quy tắc mà nó chứa, các chuỗi tích hợp sẵn đại diện cho các điểm cắm (hook) của netfilter kích hoạt chúng. Các chuỗi quyết định thời điểm mà các quy tắc được đánh giá.
Tên của các chuỗi tích hợp sẵn phản ánh tên của hook netfilter mà chúng liên kết:
PREROUTING
: Kích hoạt bởi hookNF_IP_PRE_ROUTING
.INPUT
: Kích hoạt bởi hookNF_IP_LOCAL_IN
.FORWARD
: Kích hoạt bởi hookNF_IP_FORWARD
.OUTPUT
: Kích hoạt bởi hookNF_IP_LOCAL_OUT
.POSTROUTING
: Kích hoạt bởi hookNF_IP_POST_ROUTING
.
Các Bảng Có Sẵn
Hãy cùng xem qua các bảng khác nhau mà iptables cung cấp. Những bảng này đại diện cho các tập hợp quy tắc riêng biệt, được tổ chức theo từng lĩnh vực để đánh giá gói tin.
Bảng Filter
Bảng filter là một trong những bảng được sử dụng phổ biến nhất trong iptables. Bảng này được dùng để quyết định xem có cho phép gói tin tiếp tục đến đích dự định hay từ chối yêu cầu của nó. Trong thuật ngữ tường lửa, quá trình này được gọi là “lọc” gói tin. Bảng filter cung cấp phần lớn các chức năng mà người ta liên tưởng đến khi nói về tường lửa.
Bảng NAT
Bảng nat được dùng để triển khai các quy tắc chuyển đổi địa chỉ mạng (NAT). Khi gói tin đi vào ngăn xếp mạng, các quy tắc trong bảng này sẽ xác định xem có nên và làm thế nào để sửa đổi địa chỉ nguồn hoặc đích của gói tin nhằm ảnh hưởng đến cách định tuyến của gói tin và lưu lượng phản hồi. Thông thường, điều này được sử dụng để định tuyến gói tin đến các mạng khi không thể truy cập trực tiếp.
Bảng Mangle
Bảng mangle được sử dụng để thay đổi các tiêu đề IP của gói tin theo nhiều cách khác nhau. Ví dụ, bạn có thể điều chỉnh giá trị TTL (Time to Live) của gói tin, kéo dài hoặc rút ngắn số bước nhảy mạng hợp lệ mà gói tin có thể thực hiện. Các tiêu đề IP khác cũng có thể được thay đổi tương tự.
Bảng này cũng cho phép gán một “đánh dấu” nội bộ (kernel mark) cho gói tin nhằm mục đích xử lý thêm trong các bảng khác hoặc bởi các công cụ mạng khác. Đánh dấu này không làm thay đổi gói tin thực tế mà chỉ được thêm vào biểu diễn của gói tin trong nhân hệ thống.
Bảng Raw
Bảng raw có chức năng rất cụ thể. Mục đích duy nhất của nó là cung cấp cơ chế đánh dấu gói tin để loại trừ chúng khỏi quá trình theo dõi kết nối (connection tracking).
Bảng Security
Bảng security được dùng để gán các đánh dấu ngữ cảnh bảo mật nội bộ của SELinux cho gói tin, từ đó ảnh hưởng đến cách mà SELinux hoặc các hệ thống khác có khả năng hiểu ngữ cảnh bảo mật xử lý gói tin. Các đánh dấu này có thể được áp dụng theo từng gói tin hoặc theo từng kết nối.
Mối Quan Hệ Giữa Các Chuỗi và Các Bảng
Nếu có ba bảng cùng có chuỗi PREROUTING, thì các chuỗi đó sẽ được đánh giá theo thứ tự nào?
Bảng dưới đây chỉ ra các chuỗi có sẵn trong mỗi bảng của iptables khi đọc từ trái sang phải. Ví dụ, ta có thể nhận thấy rằng bảng raw có cả chuỗi PREROUTING và OUTPUT. Khi đọc từ trên xuống dưới, bảng cũng hiển thị thứ tự gọi của từng chuỗi khi hook netfilter liên quan được kích hoạt.
Một số điều cần lưu ý: Trong biểu diễn dưới đây, bảng nat được chia thành các phần cho các hoạt động DNAT (những thao tác thay đổi địa chỉ đích của gói tin) và SNAT (những thao tác thay đổi địa chỉ nguồn) nhằm hiển thị thứ tự của chúng rõ ràng hơn. Ngoài ra, các hàng đại diện cho các điểm mà quyết định định tuyến được thực hiện và nơi connection tracking được kích hoạt cũng được đưa vào để cung cấp một cái nhìn tổng quát về các quá trình diễn ra:
Tables↓/Chains→ PREROUTING INPUT FORWARD OUTPUT POSTROUTING (routing decision) ✓ raw ✓ ✓ (connection tracking enabled) ✓ ✓ mangle ✓ ✓ ✓ ✓ ✓ nat (DNAT) ✓ ✓ (routing decision) ✓ ✓ filter ✓ ✓ ✓ security ✓ ✓ ✓ nat (SNAT) ✓ ✓
Khi một gói tin kích hoạt một hook của netfilter, các chuỗi liên quan sẽ được xử lý theo thứ tự từ trên xuống dưới như được liệt kê trong bảng ở trên. Các hook (cột) mà một gói tin kích hoạt phụ thuộc vào việc gói tin đó đến hay đi, các quyết định định tuyến được đưa ra, và liệu gói tin có vượt qua các tiêu chí lọc hay không.
Một số sự kiện nhất định sẽ khiến cho chuỗi của một bảng bị bỏ qua trong quá trình xử lý. Ví dụ, chỉ có gói tin đầu tiên trong một kết nối mới được đánh giá theo các quy tắc NAT. Mọi quyết định NAT được thực hiện cho gói tin đầu tiên sẽ được áp dụng cho tất cả các gói tin sau đó trong kết nối mà không cần đánh giá thêm. Các phản hồi cho các kết nối đã được NAT sẽ tự động áp dụng các quy tắc NAT ngược lại để định tuyến một cách chính xác.
Thứ Tự Duyệt Chuỗi
Giả sử rằng máy chủ đã biết cách định tuyến gói tin và các quy tắc tường lửa cho phép gói tin đó được truyền đi, các luồng sau đây thể hiện đường đi mà gói tin sẽ trải qua trong các tình huống khác nhau:
- Gói tin đến dành cho hệ thống cục bộ:
PREROUTING
->INPUT
- Gói tin đến dành cho máy chủ khác:
PREROUTING
->FORWARD
->POSTROUTING
- Gói tin được tạo ra cục bộ:
OUTPUT
->POSTROUTING
Nếu kết hợp thông tin trên với thứ tự được trình bày trong bảng, ta thấy rằng một gói tin đến dành cho hệ thống cục bộ sẽ được đánh giá đầu tiên qua các chuỗi PREROUTING của các bảng raw, mangle và nat. Sau đó, gói tin sẽ đi qua các chuỗi INPUT của các bảng mangle, filter, security và nat trước khi cuối cùng được chuyển đến socket cục bộ.
Quy Tắc IPTables
Các quy tắc được đặt trong một chuỗi cụ thể của một bảng cụ thể. Khi chuỗi được gọi, gói tin sẽ được so sánh lần lượt với từng quy tắc trong chuỗi đó. Mỗi quy tắc bao gồm hai phần: phần điều kiện khớp (matching component) và phần hành động (action component).
Điều Kiện Khớp (Matching)
Phần điều kiện khớp của một quy tắc xác định các tiêu chí mà gói tin cần đáp ứng để kích hoạt hành động (hoặc “target”) liên quan.
Hệ thống điều kiện khớp rất linh hoạt và có thể được mở rộng đáng kể nhờ các tiện ích mở rộng của iptables. Các quy tắc có thể được xây dựng để khớp theo loại giao thức, địa chỉ đích hay nguồn, cổng đích hay nguồn, mạng đích hay nguồn, giao diện vào hay ra, tiêu đề, trạng thái kết nối, và nhiều tiêu chí khác. Các tiêu chí này có thể được kết hợp để tạo ra những tập hợp quy tắc phức tạp nhằm phân biệt lưu lượng khác nhau.
Hành Động (Targets)
“Target” đề cập đến hành động được thực hiện khi gói tin đáp ứng các tiêu chí khớp của quy tắc. Các target thường được chia thành hai loại:
- Target kết thúc (Terminating targets): Thực hiện hành động khiến cho quá trình đánh giá trong chuỗi bị dừng lại và trả lại quyền điều khiển cho hook netfilter. Tùy thuộc vào giá trị trả về, hook có thể loại bỏ gói tin hoặc cho phép nó tiếp tục sang giai đoạn xử lý tiếp theo.
- Target không kết thúc (Non-terminating targets): Thực hiện hành động và cho phép quá trình đánh giá trong chuỗi tiếp tục. Mặc dù mỗi chuỗi cuối cùng phải trả về một quyết định kết thúc, nhưng trước đó có thể thực hiện bất kỳ số lượng target không kết thúc nào.
Nhảy Chuyển đến Các Chuỗi Tự Định Nghĩa
Ngoài ra, còn có một loại target đặc biệt không kết thúc: target nhảy (jump target). Target nhảy là những hành động khiến quá trình đánh giá chuyển sang một chuỗi khác để xử lý bổ sung. Chúng ta đã đề cập đến các chuỗi tích hợp sẵn liên kết với các hook netfilter kích hoạt chúng. Tuy nhiên, iptables cũng cho phép quản trị viên tự tạo các chuỗi cho mục đích tổ chức.
Quy tắc có thể được đặt trong các chuỗi tự định nghĩa theo cách tương tự như trong các chuỗi tích hợp sẵn. Sự khác biệt là các chuỗi tự định nghĩa chỉ có thể được tiếp cận bằng cách “nhảy” từ một quy tắc (chúng không được đăng ký với hook netfilter).
Các chuỗi tự định nghĩa hoạt động như phần mở rộng của chuỗi đã gọi chúng. Ví dụ, trong một chuỗi tự định nghĩa, nếu danh sách quy tắc kết thúc hoặc nếu một target RETURN được kích hoạt bởi quy tắc khớp, quá trình đánh giá sẽ quay lại chuỗi đã gọi. Quá trình đánh giá cũng có thể nhảy sang các chuỗi tự định nghĩa khác.
Cấu trúc này cho phép tổ chức quy tắc tốt hơn và cung cấp khung cần thiết cho những nhánh xử lý mạnh mẽ hơn.
IPTables và Theo Dõi Kết Nối (Connection Tracking)
Hệ thống theo dõi kết nối được xây dựng trên nền tảng khung netfilter đã được giới thiệu khi chúng ta bàn về bảng raw và tiêu chí khớp trạng thái kết nối.
Theo dõi kết nối cho phép iptables đưa ra quyết định về các gói tin dựa trên bối cảnh của một kết nối đang diễn ra. Hệ thống này cung cấp cho iptables chức năng cần thiết để thực hiện các thao tác “stateful”.
Quá trình theo dõi kết nối được áp dụng rất sớm sau khi gói tin đi vào ngăn xếp mạng. Các chuỗi của bảng raw và một số kiểm tra hợp lý là những logic duy nhất được thực hiện trên gói tin trước khi liên kết chúng với một kết nối.
Các Trạng Thái Có Sẵn
Các kết nối được hệ thống theo dõi kết nối quản lý sẽ có một trong các trạng thái sau:
NEW
: Khi một gói tin đến không liên kết với bất kỳ kết nối hiện có nào, nhưng không bị coi là không hợp lệ khi là gói tin đầu tiên, một kết nối mới sẽ được thêm vào hệ thống với nhãn này. Điều này xảy ra đối với cả các giao thức có kết nối (như TCP) và các giao thức không kết nối (như UDP).ESTABLISHED
: Một kết nối chuyển từ trạng thái NEW sang ESTABLISHED khi nhận được phản hồi hợp lệ từ phía ngược lại. Đối với TCP, điều này có nghĩa là nhận được SYN/ACK; còn đối với UDP và ICMP, tức là nhận được phản hồi với địa chỉ nguồn và đích được hoán đổi.RELATED
: Các gói tin không phải là một phần của kết nối hiện có nhưng có liên quan đến một kết nối đã có trong hệ thống được gán nhãn là RELATED. Điều này có thể là một kết nối trợ giúp (như trong truyền dữ liệu FTP) hoặc phản hồi ICMP đối với các cố gắng kết nối từ giao thức khác.INVALID
: Các gói tin có thể được đánh dấu là INVALID nếu chúng không liên kết với bất kỳ kết nối hiện có nào, không phù hợp để mở một kết nối mới, không thể xác định, hoặc không thể định tuyến được vì nhiều lý do khác.UNTRACKED
: Các gói tin được đánh dấu là UNTRACKED nếu chúng đã được nhắm mục tiêu trong một chuỗi của bảng raw nhằm bỏ qua quá trình theo dõi.SNAT
: Đây là trạng thái ảo được đặt khi địa chỉ nguồn bị thay đổi bởi các thao tác NAT. Hệ thống theo dõi kết nối sử dụng thông tin này để biết rằng cần điều chỉnh lại địa chỉ nguồn trong các gói tin phản hồi.DNAT
: Đây là trạng thái ảo được đặt khi địa chỉ đích bị thay đổi bởi các thao tác NAT. Hệ thống theo dõi kết nối sử dụng thông tin này để biết rằng cần điều chỉnh lại địa chỉ đích khi định tuyến các gói tin phản hồi.
Các trạng thái được theo dõi cho phép quản trị viên xây dựng các quy tắc nhắm chính xác vào các điểm quan trọng trong vòng đời của một kết nối, từ đó đảm bảo quy tắc được triển khai một cách kỹ lưỡng và an toàn hơn.
Kết Luận
Khung lọc gói tin netfilter và tường lửa iptables là nền tảng cho hầu hết các giải pháp tường lửa trên máy chủ Linux. Các hook của netfilter được đặt rất sát với ngăn xếp mạng, cho phép kiểm soát mạnh mẽ các gói tin khi chúng được hệ thống xử lý. Tường lửa iptables tận dụng các khả năng này để cung cấp một phương pháp linh hoạt và mở rộng nhằm truyền đạt yêu cầu chính sách đến nhân hệ thống. Khi hiểu rõ cách các thành phần này hoạt động cùng nhau, bạn sẽ có thể sử dụng chúng một cách hiệu quả để kiểm soát và bảo vệ môi trường máy chủ của mình.
Nếu bạn muốn tìm hiểu thêm về cách lựa chọn các chính sách iptables hiệu quả, hãy xem hướng dẫn liên quan.
Những hướng dẫn dưới đây có thể giúp bạn bắt đầu triển khai các quy tắc tường lửa iptables:
- Cách Thiết Lập Tường Lửa Sử Dụng Iptables
- Iptables Essentials: Các Quy Tắc và Lệnh Tường Lửa Thông Dụng
- Cách Thiết Lập Tường Lửa với UFW trên Ubuntu 22.04
- Cách Thiết Lập Tường Lửa Sử Dụng firewalld trên Rocky Linux 8
- Cách Thiết Lập Tường Lửa Iptables để Bảo Vệ Lưu Lượng Giữa Các Máy Chủ của Bạn