iptables คือ Firewall ที่มาพร้อมกับ Linux Kernel ทุก Distribution มาหลายสิบปี ทำหน้าที่กรอง Network Packet ที่เข้าและออกจาก Server โดยใช้กฎ (Rules) ที่กำหนดว่า Packet ใดจะถูก Accept, Drop, หรือ Reject ความเข้าใจ iptables จึงเป็นพื้นฐานสำคัญสำหรับ Linux System Admin เพราะแม้จะมีเครื่องมือที่ใช้งานง่ายกว่าอย่าง UFW หรือ Firewalld แต่ทั้งคู่ก็ทำงานอยู่บน iptables อยู่ดี
บทความนี้อธิบายหลักการทำงานของ iptables ตั้งแต่ Tables, Chains, Targets, การเพิ่มและลบ Rules, การตั้งค่า Default Policy, การบันทึก Rules ให้คงอยู่หลัง Reboot รวมถึง Pattern ที่ใช้บ่อยบน Production Server เช่น อนุญาต SSH, HTTP, HTTPS และการป้องกัน DDoS เบื้องต้น
หลักการทำงาน: Tables, Chains และ Targets
# iptables จัดการ Packet ผ่าน 3 ชั้น:
# 1. Tables — กำหนดประเภทการ Filter
# 2. Chains — กำหนดจุดที่ Packet ถูกตรวจสอบ
# 3. Targets — กำหนดว่าจะทำอะไรกับ Packet
# Tables หลัก:
# filter — ตารางหลัก (default) ใช้กรอง Packet
# nat — ใช้แปลง IP/Port (NAT, Port Forwarding)
# mangle — ใช้แก้ไข Packet Header
# Chains ใน filter table:
# INPUT — Packet ที่เข้าสู่ Server โดยตรง
# OUTPUT — Packet ที่ออกจาก Server
# FORWARD — Packet ที่ผ่าน Server (ใช้เมื่อ Server เป็น Router)
# Targets (ผลลัพธ์ของ Rule):
# ACCEPT — อนุญาต Packet ผ่าน
# DROP — ทิ้ง Packet โดยไม่ตอบกลับ (Stealth)
# REJECT — ปฏิเสธ Packet พร้อมส่ง Error กลับ
# LOG — บันทึก Log แล้วส่งต่อให้ Rule ถัดไป
# การไหลของ Packet:
# Packet เข้า → INPUT chain → Process บน Server
# Server ส่ง Packet → OUTPUT chain → Network
# Packet ผ่าน Router → FORWARD chain → Network
ดู Rules ที่มีอยู่
# ดู Rules ทั้งหมด (filter table)
sudo iptables -L
# ดูแบบละเอียด พร้อม Line Number และ Packet Count
sudo iptables -L -v -n --line-numbers
# ดูเฉพาะ Chain ที่ต้องการ
sudo iptables -L INPUT -v -n --line-numbers
sudo iptables -L OUTPUT -v -n --line-numbers
# ดู NAT table
sudo iptables -t nat -L -v -n --line-numbers
# ดู Default Policy (บนสุดของแต่ละ Chain)
# ตัวอย่าง Output:
# Chain INPUT (policy ACCEPT) ← Default Policy คือ ACCEPT
# Chain FORWARD (policy DROP) ← Default Policy คือ DROP
# Chain OUTPUT (policy ACCEPT)
# ดูด้วยรูปแบบที่ copy-paste กลับใช้ได้
sudo iptables -S
เพิ่ม Rules พื้นฐาน
# Syntax พื้นฐาน:
# iptables -A CHAIN -p PROTOCOL --dport PORT -j TARGET
# -A = Append (เพิ่มท้าย Chain)
# -I = Insert (เพิ่มต้น Chain หรือระบุตำแหน่ง)
# -p = Protocol (tcp, udp, icmp, all)
# --dport = Destination Port
# -j = Jump to Target
# อนุญาต SSH (port 22)
sudo iptables -A INPUT -p tcp --dport 22 -j ACCEPT
# อนุญาต HTTP และ HTTPS
sudo iptables -A INPUT -p tcp --dport 80 -j ACCEPT
sudo iptables -A INPUT -p tcp --dport 443 -j ACCEPT
# อนุญาต Loopback Interface (จำเป็นสำหรับ Local Service)
sudo iptables -A INPUT -i lo -j ACCEPT
# อนุญาต Established Connections (สำคัญมาก — ป้องกันการ Drop การตอบกลับ)
sudo iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
# อนุญาต ICMP (ping) จาก IP เฉพาะ
sudo iptables -A INPUT -p icmp -s 192.168.1.0/24 -j ACCEPT
# บล็อก IP เฉพาะ
sudo iptables -A INPUT -s 203.0.113.10 -j DROP
# อนุญาต Port เฉพาะจาก IP เฉพาะ (เช่น MySQL จาก App Server)
sudo iptables -A INPUT -p tcp -s 10.0.0.5 --dport 3306 -j ACCEPT
ตั้งค่า Default Policy
Default Policy คือสิ่งที่ iptables จะทำกับ Packet ที่ไม่ตรงกับ Rule ใดเลย การตั้ง Default Policy เป็น DROP แล้วเปิดเฉพาะ Port ที่ต้องการ (Allowlist approach) เป็น Best Practice สำหรับ Production Server
# ดู Default Policy ปัจจุบัน
sudo iptables -L | grep "policy"
# ตั้ง Default Policy เป็น DROP สำหรับ INPUT
# ⚠️ ต้องเพิ่ม Rules อนุญาต SSH และ Established ก่อน มิฉะนั้นจะถูก Lock out
sudo iptables -P INPUT DROP
sudo iptables -P FORWARD DROP
sudo iptables -P OUTPUT ACCEPT # ส่วนใหญ่ปล่อย OUTPUT ไว้ ACCEPT
# ลำดับที่ถูกต้องสำหรับ Secure Firewall:
# 1. อนุญาต Loopback ก่อน
sudo iptables -A INPUT -i lo -j ACCEPT
# 2. อนุญาต Established connections
sudo iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
# 3. อนุญาต SSH (ก่อนตั้ง Default DROP เพื่อป้องกัน Lock out)
sudo iptables -A INPUT -p tcp --dport 22 -j ACCEPT
# 4. อนุญาต Web
sudo iptables -A INPUT -p tcp --dport 80 -j ACCEPT
sudo iptables -A INPUT -p tcp --dport 443 -j ACCEPT
# 5. ตั้ง Default DROP
sudo iptables -P INPUT DROP
ลบและจัดการ Rules
# ลบ Rule ตาม Line Number (ดูจาก --line-numbers ก่อน)
sudo iptables -L INPUT --line-numbers
sudo iptables -D INPUT 3 # ลบ Rule บรรทัดที่ 3
# ลบ Rule โดยระบุ Rule เหมือนตอนเพิ่ม (แต่ใช้ -D แทน -A)
sudo iptables -D INPUT -p tcp --dport 80 -j ACCEPT
# แทรก Rule ที่ตำแหน่งเฉพาะ (เพิ่มเป็นลำดับที่ 1)
sudo iptables -I INPUT 1 -s 10.0.0.0/8 -j ACCEPT
# เคลียร์ Rules ทั้งหมดใน Chain
sudo iptables -F INPUT # Flush INPUT chain
sudo iptables -F # Flush ทุก Chain ใน filter table
# Reset ทุกอย่างกลับเป็น ACCEPT (ฉุกเฉิน — ถ้า Lock out ตัวเอง)
sudo iptables -F
sudo iptables -P INPUT ACCEPT
sudo iptables -P FORWARD ACCEPT
sudo iptables -P OUTPUT ACCEPT
บันทึก Rules ให้คงอยู่หลัง Reboot
iptables Rules ที่ตั้งผ่าน Command Line จะหายไปเมื่อ Reboot ต้องบันทึกด้วย iptables-persistent (Debian/Ubuntu) หรือ iptables-services (RHEL/Rocky)
# Ubuntu/Debian — ติดตั้ง iptables-persistent
sudo apt install iptables-persistent
# ระหว่างติดตั้งจะถามว่าจะ Save Rules ปัจจุบันหรือไม่ → ตอบ Yes
# บันทึก Rules ปัจจุบัน
sudo netfilter-persistent save
# หรือ
sudo iptables-save | sudo tee /etc/iptables/rules.v4
sudo ip6tables-save | sudo tee /etc/iptables/rules.v6
# โหลด Rules จากไฟล์ (ทำงานอัตโนมัติตอน Boot)
sudo netfilter-persistent reload
# RHEL/Rocky Linux
sudo dnf install iptables-services
sudo systemctl enable iptables
sudo service iptables save
# Rules ถูกบันทึกที่ /etc/sysconfig/iptables
# ดูไฟล์ที่บันทึกไว้
cat /etc/iptables/rules.v4
Rules ที่ใช้บ่อยบน Production Server
# จำกัด Rate SSH (ป้องกัน Brute Force) — อนุญาตสูงสุด 5 ครั้งต่อนาทีต่อ IP
sudo iptables -A INPUT -p tcp --dport 22 -m state --state NEW -m recent --set
sudo iptables -A INPUT -p tcp --dport 22 -m state --state NEW -m recent --update \
--seconds 60 --hitcount 5 -j DROP
# บล็อก IP Range ทั้ง Subnet
sudo iptables -A INPUT -s 198.51.100.0/24 -j DROP
# อนุญาตเฉพาะ IP จาก Thailand (ตัวอย่างแนวคิด — ใช้ ipset จริง)
# sudo ipset create th_ips hash:net
# sudo ipset add th_ips 1.0.128.0/17
# sudo iptables -A INPUT -m set --match-set th_ips src -j ACCEPT
# ป้องกัน SYN Flood
sudo iptables -A INPUT -p tcp --syn -m limit --limit 1/s --limit-burst 3 -j ACCEPT
sudo iptables -A INPUT -p tcp --syn -j DROP
# บล็อก Invalid Packets
sudo iptables -A INPUT -m state --state INVALID -j DROP
# อนุญาต DNS (สำหรับ Server ที่ทำ DNS Resolver)
sudo iptables -A INPUT -p udp --dport 53 -j ACCEPT
sudo iptables -A INPUT -p tcp --dport 53 -j ACCEPT
# อนุญาต NTP
sudo iptables -A INPUT -p udp --dport 123 -j ACCEPT
# Log Packet ที่ถูก Drop (ก่อน Rule DROP สุดท้าย)
sudo iptables -A INPUT -j LOG --log-prefix "iptables-DROP: " --log-level 4
NAT และ Port Forwarding
# เปิด IP Forwarding (จำเป็นสำหรับ NAT)
echo 1 | sudo tee /proc/sys/net/ipv4/ip_forward
# ถาวร: เพิ่มใน /etc/sysctl.conf
echo "net.ipv4.ip_forward = 1" | sudo tee -a /etc/sysctl.conf
sudo sysctl -p
# NAT / Masquerade (Server เป็น Gateway สำหรับ Private Network)
# Interface ออก Internet คือ eth0, Subnet ภายใน 10.0.0.0/24
sudo iptables -t nat -A POSTROUTING -s 10.0.0.0/24 -o eth0 -j MASQUERADE
# Port Forwarding — ส่ง Traffic port 8080 ไปที่ Server ภายใน
sudo iptables -t nat -A PREROUTING -p tcp --dport 8080 -j DNAT \
--to-destination 10.0.0.5:80
# อนุญาต FORWARD สำหรับ Port ที่ Forward
sudo iptables -A FORWARD -p tcp -d 10.0.0.5 --dport 80 -m state \
--state NEW,ESTABLISHED,RELATED -j ACCEPT
Script ตั้งค่า Firewall ทั้งระบบ
#!/bin/bash
# /usr/local/bin/setup-firewall.sh
# Firewall Script สำหรับ Web Server (HTTP, HTTPS, SSH)
set -e
# ล้าง Rules เดิมทั้งหมด
iptables -F
iptables -X
iptables -t nat -F
iptables -t nat -X
iptables -t mangle -F
iptables -t mangle -X
# Default Policy: DROP ทุกอย่าง
iptables -P INPUT DROP
iptables -P FORWARD DROP
iptables -P OUTPUT ACCEPT
# อนุญาต Loopback
iptables -A INPUT -i lo -j ACCEPT
# อนุญาต Established Connections
iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
# บล็อก Invalid Packets
iptables -A INPUT -m state --state INVALID -j DROP
# ป้องกัน SYN Flood
iptables -A INPUT -p tcp --syn -m limit --limit 25/s --limit-burst 50 -j ACCEPT
iptables -A INPUT -p tcp --syn -j DROP
# SSH: จำกัด Rate (5 connections/นาที)
iptables -A INPUT -p tcp --dport 22 -m state --state NEW \
-m recent --set --name SSH
iptables -A INPUT -p tcp --dport 22 -m state --state NEW \
-m recent --update --seconds 60 --hitcount 5 --name SSH -j DROP
iptables -A INPUT -p tcp --dport 22 -j ACCEPT
# HTTP และ HTTPS
iptables -A INPUT -p tcp --dport 80 -j ACCEPT
iptables -A INPUT -p tcp --dport 443 -j ACCEPT
# ICMP (Ping) — จำกัด Rate
iptables -A INPUT -p icmp --icmp-type echo-request \
-m limit --limit 1/s -j ACCEPT
# Log ก่อน DROP
iptables -A INPUT -j LOG --log-prefix "FW-DROP: " --log-level 4
# บันทึก Rules
netfilter-persistent save 2>/dev/null || iptables-save > /etc/iptables/rules.v4
echo "✅ Firewall configured"
echo ""
echo "Rules ปัจจุบัน:"
iptables -L -n --line-numbers
ตรวจสอบ Log
# ดู Log ที่ iptables บันทึกไว้
sudo grep "FW-DROP\|iptables-DROP" /var/log/kern.log | tail -20
sudo journalctl -k | grep "FW-DROP" | tail -20
# ตัวอย่าง Log:
# Apr 16 10:23:45 web-prod-01 kernel: FW-DROP: IN=eth0 OUT= \
# MAC=... SRC=45.33.32.156 DST=10.0.0.1 LEN=60 TOS=0x00 \
# PREC=0x00 TTL=53 ID=0 DF PROTO=TCP SPT=54321 DPT=3306 ...
# SRC = IP ต้นทางที่พยายามเชื่อมต่อ
# DPT = Destination Port ที่พยายาม
# นับ IP ที่พยายามเชื่อมต่อมากที่สุด
sudo grep "FW-DROP" /var/log/kern.log | \
grep -oP 'SRC=\K[0-9.]+' | \
sort | uniq -c | sort -rn | head -10
สรุป
iptables ทำงานผ่าน Tables (filter, nat, mangle), Chains (INPUT, OUTPUT, FORWARD), และ Targets (ACCEPT, DROP, REJECT, LOG) Rule ถูกตรวจสอบตามลำดับจากบนลงล่าง ดังนั้นลำดับการเพิ่ม Rule จึงสำคัญมาก การตั้งค่า Firewall ที่ปลอดภัยควรเพิ่ม Rule อนุญาต Loopback, Established Connections, และ SSH ก่อน แล้วจึงตั้ง Default Policy เป็น DROP เพื่อป้องกันการ Lock out ตัวเอง การบันทึก Rules ด้วย iptables-persistent หรือ netfilter-persistent จะทำให้ Rules คงอยู่หลัง Reboot สำหรับ Production Server ควรใช้ Rate Limiting บน SSH และ LOG Packets ที่ถูก DROP เพื่อ Monitoring
แนะนำบริการ DE
การตั้งค่า iptables บน Server ต้องการสิทธิ์ Root และต้องระวังการ Lock out ตัวเองหากตั้งค่าผิด Cloud VPS ของ DE ให้ Root Access เต็มรูปแบบพร้อม Console Access ผ่าน Web Panel ทำให้สามารถแก้ไข Firewall Rules ได้แม้จะ SSH เข้าไม่ได้ เหมาะสำหรับการทดลองตั้งค่า Security Rules บน Production Server
หากต้องการโฮสต์เว็บไซต์โดยมี Firewall จัดการอัตโนมัติโดยไม่ต้องตั้งค่า iptables เอง Cloud Hosting ของ DE มีระบบป้องกัน DDoS และ Firewall พร้อมใช้งานตั้งแต่แรก

