Quick start: View and manage the conntrack table in 5 minutes
When Linux operates as a NAT gateway, load balancer, or runs an iptables/nftables firewall, the kernel quietly tracks every network session. The conntrack-tools utility lets you interact directly with this tracking data instead of parsing complex raw files in /proc.
Install the package on Debian/Ubuntu:
sudo apt update && sudo apt install -y conntrack
On RHEL, Rocky Linux, or CentOS Stream:
sudo dnf install -y conntrack-tools
Quickly check the total number of connections currently tracked by the kernel:
sudo conntrack -C
List the first 10 TCP connections in the ESTABLISHED state:
sudo conntrack -L -p tcp --status ESTABLISHED | head -n 10
Filter sessions destined for an internal database server (e.g., IP 10.0.0.50):
sudo conntrack -L -d 10.0.0.50
Need to immediately kill all connections from an IP flooding your traffic? Use the -D flag:
sudo conntrack -D -s 203.0.113.88
Under the hood: What is Conntrack and how does it work?
Think of your server like an office building lobby handling thousands of visitors every day. When a new visitor walks in, the security guard checks their ID, logs their visit in a ledger, and only then calls the elevator. If that person returns minutes later, the guard just glances at the book: "Already checked in, go right ahead." No one has to go through the full screening process again.
Conntrack (Connection Tracking) serves as that exact duty log for the Linux kernel. It is a core subsystem within the Netfilter framework. Thanks to conntrack, the firewall can recognize which session a packet belongs to and run classic rules like this:
iptables -A INPUT -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT
For every packet traversing the system, the kernel extracts its 5-tuple: Source IP, Destination IP, Source Port, Destination Port, and Protocol. This tuple is hashed and stored directly in an in-memory hash table in RAM.
4 connection states you need to know
- NEW: The first packet establishing a data stream, typically a TCP SYN flag.
- ESTABLISHED: A bidirectional session confirmed after completing the 3-way handshake.
- RELATED: A secondary connection spawned by an existing session, such as a passive FTP data channel or an ICMP unreachable error packet.
- UNTRACKED: Packets bypassed and ignored by connection tracking, usually marked via the
rawtable to conserve system resources.
How to read a conntrack log entry
Running the command conntrack -L outputs records formatted like this:
tcp 6 431999 ESTABLISHED src=192.168.1.15 dst=1.1.1.1 sport=54212 dport=443 src=1.1.1.1 dst=192.168.1.15 sport=443 dport=54212 [ASSURED] mark=0 use=1
Breaking down each field:
tcp 6: Protocol name alongside its standard IP protocol number (TCP is 6, UDP is 17).431999: Countdown TTL in seconds. Once this timer expires without new packets, the entry is evicted.ESTABLISHED: The current state of the TCP session.- The two
src/dst/sport/dporttuples: The first represents the outbound flow (original direction), and the second represents the expected return flow (reply direction). [ASSURED]: Indicates the kernel has seen bidirectional traffic in both directions—it is no longer a one-way connection.
Real-world troubleshooting: When the conntrack table overflows
The symptoms can be bizarre: CPU sits at only 30%, plenty of free RAM, network throughput nowhere near saturating a 1Gbps link, yet APIs frequently time out during peak traffic hours. Pinging the gateway reveals intermittent 15-20% packet loss bursts.
Network switches and physical cables check out fine. Only after checking dmesg -T does the real culprit appear:
nf_conntrack: table full, dropping packet
In this scenario, the server was handling NAT for a Kubernetes cluster running over 80 microservices. Tens of thousands of short-lived HTTP requests were opening and closing every second. The conntrack table hit its default ceiling of 65,536 entries. To prevent RAM exhaustion, the kernel automatically dropped any incoming new packets.
Check your current capacity limits
View the maximum number of entries allowed by the kernel:
sysctl net.netfilter.nf_conntrack_max
View the number of buckets in the hash table:
cat /sys/module/nf_conntrack/parameters/hashsize
Safe sizing formula and RAM calculation
The optimal ratio between nf_conntrack_max and hashsize is 4:1 or 8:1. On a 64-bit architecture, each tracking entry consumes approximately 320 bytes of memory.
Scaling the table to 1,048,576 entries (~1M connections)? That requires only about 335 MB of RAM—a negligible cost on modern servers equipped with 32GB or 64GB of RAM.
Apply changes immediately at runtime:
sudo sysctl -w net.netfilter.nf_conntrack_max=1048576
echo 262144 | sudo tee /sys/module/nf_conntrack/parameters/hashsize
To persist these values across system reboots, append them to /etc/sysctl.d/99-conntrack.conf:
net.netfilter.nf_conntrack_max = 1048576
net.netfilter.nf_conntrack_tcp_timeout_established = 21600
net.netfilter.nf_conntrack_tcp_timeout_close_wait = 60
net.netfilter.nf_conntrack_tcp_timeout_fin_wait = 30
net.netfilter.nf_conntrack_tcp_timeout_time_wait = 30
Pin the hashsize parameter in /etc/modprobe.d/conntrack.conf:
options nf_conntrack hashsize=262144
Reload all sysctl configuration files:
sudo sysctl --system
Production battle-tested tips for high-load servers
- Lower TCP ESTABLISHED timeouts immediately: By default, Linux keeps established sessions alive for 432,000 seconds (5 full days). If a client drops offline abruptly without sending a FIN or RST packet, that entry lingers in the table for nearly a week. Reduce this timeout to 6 hours (21,600 seconds) or 2 hours for public-facing web servers.
- Enable NOTRACK for heavy stateless traffic: If your server runs HAProxy, an Nginx reverse proxy, or a public DNS resolver, you do not necessarily need stateful tracking for every single packet. Bypassing conntrack via the
rawtable frees up substantial CPU and RAM resources:
sudo iptables -t raw -A PREROUTING -p tcp -m multiport --dports 80,443 -j NOTRACK
sudo iptables -t raw -A PREROUTING -p udp --dport 53 -j NOTRACK
- Capture real-time events during debugging: The following command allows you to observe sessions being created and destroyed in real time:
sudo conntrack -E -e NEW,DESTROY
- Configure proactive alerts before outages hit: Monitor the ratio
node_nf_conntrack_entries / node_nf_conntrack_entries_limitin Grafana. Set up alerting when utilization reaches 75-80%. This gives your infrastructure team ample time to intervene before the table fills up and packets start dropping in the middle of the night.

