$ sudo nft list ruleset

Firewalls

A firewall checks each network packet or connection against a list of rules and decides to allow it or drop it. Rules match on things like source and destination IP, port, protocol and, in a stateful firewall, whether the packet belongs to a connection that was already allowed. Firewalls run on a single host (Linux nftables, Windows Defender Firewall), at the network edge (appliances from Palo Alto, Fortinet, Cisco), and in the cloud as security groups and network ACLs.

A stateful firewall at work

$ nft list ruleset
A stateful firewall deciding packet by packet
INTERNET 203.0.113.9 FIREWALL stateful WEB SERVER 10.0.1.10 SYN → :443 rule 1 allow · track SYN → :443 SYN-ACK SYN-ACK (state ok) SYN → :22 no match → DROP SYN → 198.51.100.7:25 egress: DROP
NO.STEPFROMTOTYPEINFO
101203.0.113.910.0.1.10ACCEPTtcp dport 443 · rule 1 · conntrack: NEW
20210.0.1.10203.0.113.9ACCEPTtcp sport 443 · ct state established · rule 2
303203.0.113.910.0.1.10DROPtcp dport 22 · no rule · policy drop
40410.0.1.10198.51.100.7DROPtcp dport 25 · output policy drop
  1. Rules: (1) allow TCP 443 in, (2) allow packets of established connections, (3) drop everything else, in and out.
  2. A new HTTPS connection matches rule 1. The firewall forwards it and records the flow in its connection-tracking table.
  3. The server's reply has no rule of its own. It passes because it belongs to a tracked connection: that is what stateful means.
  4. Someone probes SSH on port 22. No rule allows it, so the default deny drops it silently.
  5. The server itself tries to open an SMTP connection out. Egress filtering blocks it, a common sign of malware or a leak.

The same rules written for Linux nftables:

table inet filter {
  chain input {
    type filter hook input priority 0; policy drop;
    ct state established,related accept      # replies to allowed connections
    iif "lo" accept
    tcp dport 443 accept                     # HTTPS from anywhere
    ip saddr 10.0.0.0/16 tcp dport 22 accept # SSH only from inside the VPC
  }
}

Types of firewall

Type Decides on Strength Weakness
Stateless packet filter Each packet alone: IPs, ports, protocol Very fast, simple Must open return traffic explicitly; easy to get wrong
Stateful Packet + connection-tracking table Replies allowed automatically; the default today Table can fill up under heavy load or attack
Application-level / proxy The application protocol (HTTP, SQL) Can inspect content, terminate TLS Slower, protocol-specific
Next-generation (NGFW) Apps, users, threat signatures, TLS inspection Deep visibility Cost, complexity, privacy concerns of decryption
WAF HTTP requests to a web app Blocks SQL injection, XSS, bots Only for HTTP, needs tuning

Firewalls in the cloud

  • Security groups (AWS, also GCP and Azure firewall rules) are stateful and attached to instances, load balancers and managed databases. A typical setup: the database’s group allows port 5432 only from the app’s security group, not from an IP range.
  • Network ACLs are stateless and apply to a whole subnet. Remember to allow the ephemeral return ports (1024 to 65535).
  • Kubernetes NetworkPolicies do the same between pods, enforced by the CNI plugin (Calico, Cilium).

Common mistakes

  • 0.0.0.0/0 on a database port. Exposed databases are found by scanners within hours. Allow only the subnets or security groups that need access.
  • No egress rules. Most setups allow all outbound traffic. Restricting it limits data exfiltration and malware call-backs.
  • Debugging blind. A dropped SYN looks like a timeout; a rejected one looks like “connection refused”. Test with nc -vz host port from the actual source machine, and enable flow logs (VPC Flow Logs) to see drops.
  • Treating the firewall as the only defense. Once an attacker is inside the perimeter, flat networks let them move freely. Combine with authentication on every service (zero trust).

Learning Resources

See also: TCP/IP, VPN.