Attempting to connect to a remote Linux server or local development virtual machine only for your terminal to output the immediate rejection: “ssh: connect to host 192.168.1.100 port 22: Connection refused” halts administration workflows. Unlike network timeouts (which typically indicate dropped packets or routing blackholes), a Connection refused message is an explicit TCP RST (reset) response sent back by the target host or an intervening firewall. This response confirms that the server network stack received the TCP SYN packet, but either no service is currently listening on port 22 or firewall rules actively reject the connection. This tutorial explains how to diagnose SSH daemon state, inspect listening sockets, and adjust firewall policies in Linux.
Why Does Linux Return ‘Connection Refused’ on Port 22?
Understanding the exact failure point between the SSH client and the host daemon speeds up recovery:
- OpenSSH Daemon Is Inactive or Failed: The
sshdsystem service is not running, crashed during startup, or was never installed on a clean minimal OS image. - Custom Port Configuration: The server’s
sshd_configwas modified to listen on a non-standard port (such as 2222 or 50222), causing default port 22 queries to be rejected. - Local Firewall Rules (UFW / firewalld / iptables): Uncomplicated Firewall (UFW) or
iptablesfiltering configured with an explicitREJECTtarget for incoming connections. - IP Address or Network Interface Binding Restrictions: The SSH daemon is configured to listen exclusively on the loopback interface (
127.0.0.1) rather than all available network adapters (0.0.0.0).
Step 1: Check OpenSSH Server Service Status
Log in via the server console, cloud provider VNC viewer, or local terminal to verify that the daemon is active.
- Check the status of the SSH service:
(Note: On RHEL, CentOS, or Fedora, usesudo systemctl status sshsudo systemctl status sshd). - If the service is marked as inactive (dead) or failed, start it immediately:
sudo systemctl start ssh sudo systemctl enable ssh - If the system reports “Unit ssh.service could not be found”, the OpenSSH server package is not installed. Install it using your distribution package manager:
sudo apt update && sudo apt install -y openssh-server
Step 2: Verify Listening Ports and Address Binding
Confirm that the SSH service is actively listening on TCP port 22 and bound to public interfaces.
- Use
ssto inspect active TCP listening sockets:sudo ss -tulpn | grep -E ':(22|ssh)' - Inspect the output address:
- If it displays
0.0.0.0:22and[::]:22, the daemon is properly listening on all IPv4 and IPv6 interfaces. - If it displays
127.0.0.1:22, the daemon is restricted to local connections only. - If another port number is listed (e.g.
0.0.0.0:2222), connect from your client using the-pflag:ssh -p 2222 user@host.
- If it displays
- To correct interface binding, edit the configuration file:
sudo nano /etc/ssh/sshd_config - Locate the line
#ListenAddress 0.0.0.0, uncomment it by removing the#, and ensurePort 22is declared. - Save the file (Ctrl + O, then Ctrl + X) and restart the daemon:
sudo systemctl restart ssh
Step 3: Configure UFW and firewalld Firewall Rules
Adjust local firewall policies to allow incoming TCP traffic on port 22.
- For Ubuntu and Debian (UFW):
sudo ufw status verbose sudo ufw allow 22/tcp sudo ufw reload - For RHEL, AlmaLinux, and Rocky Linux (firewalld):
sudo firewall-cmd --permanent --add-service=ssh sudo firewall-cmd --reload - For Raw iptables:
sudo iptables -A INPUT -p tcp --dport 22 -j ACCEPT
Step 4: Test Connection Verbosity from the Client
Run SSH with verbose output from your client machine to pinpoint the exact network layer dropping the connection.
- Execute SSH with the
-vvvswitch:ssh -vvv [email protected] - Analyze the output lines:
- If it halts at
Connecting to 192.168.1.100 [192.168.1.100] port 22...followed byconnect to host ... port 22: Connection refused, the host machine actively rejected the TCP SYN packet. - If it passes the connection stage and displays
Connection established, the issue was with authentication credentials rather than network connectivity.
- If it halts at
Troubleshooting Summary for SSH Connection Refused
| Diagnostic Check | Terminal Command | Expected Resolution |
|---|---|---|
| Verify Daemon Status | systemctl status ssh |
Starts and enables inactive OpenSSH server daemon |
| Check Socket Bindings | ss -tulpn | grep 22 |
Ensures daemon listens on 0.0.0.0:22 |
| Open UFW Firewall | ufw allow 22/tcp |
Permits inbound TCP handshakes through packet filter |
| Inspect Verbose Logs | ssh -vvv user@host |
Pinpoints exact handshake stage of connection refusal |
Following these systematic verification steps ensures that OpenSSH is active, correctly bound, and accessible through firewall rules across any Linux server environment.