Take the 2-minute tour ×
Super User is a question and answer site for computer enthusiasts and power users. It's 100% free, no registration required.

In the old days, we used telnet to see if a port on a remote host was open: telnet hostname port would attempt to connect to any port on any host and give you access to the raw TCP stream.

These days, the systems I work on do not have telnet installed (for security reasons), and all outbound connections to all hosts are blocked by default. Over time, it's easy to lose track of which ports are open to which hosts.

Is there another way to test if a port on a remote system is open – using a Linux system with a limited number of packages installed, and telnet is not available?

share|improve this question

7 Answers 7

up vote 49 down vote accepted

Bash has been able to access tcp & udp ports for a while. From the man page:

    If host is a valid hostname or Internet address, and port is an integer port number
    or service name, bash attempts to open a TCP connection to the corresponding socket.
    If host is a valid hostname or Internet address, and port is an integer port number
    or service name, bash attempts to open a UDP connection to the corresponding socket.

So you could use something like this:

xenon-lornix:~> cat < /dev/tcp/
SSH-2.0-OpenSSH_6.2p2 Debian-6
^C pressed here

Taa Daa!

share|improve this answer

Netcat is a useful tool:

nc 123 < /dev/null; echo $?

Will output 0 if port 123 is open, and 1 if it's closed.

share|improve this answer
This is a far more elegant and scriptable answer than my own. It is unfortunate for me that the security-conscious sysadmins who withheld telnet also withheld nc (though – strangely – not curl or wget). –  Steve HHH Jul 19 '13 at 19:51
Yes that is completely arbitrary and silly. –  thnee Jul 19 '13 at 20:10
Let the FOR statements begin! –  hydroparadise Jul 19 '13 at 21:37
awesome, thanks. –  mtyson Apr 20 at 16:28

Nice and verbose! From the man pages.
Single port:

nc -zv 80

Multiple ports:

nc -zv 22 80 8080

Range of ports:

nc -zv 20-30
share|improve this answer
Seems to be far the bestest answer, thanks. ;-) –  lpapp Nov 26 '14 at 15:42
Perfect! This outputs a clear connection succeeded/failed message with just the one line. Note that multiple ranges don't appear to work for my nc version; only the first range is tested. –  davidjb May 18 at 3:42

I found that curl may get the job done in a similar way to telnet, and curl will even tell you which protocol the listener expects.

Construct an HTTP URI from the hostname and port as the first argument to curl. If curl can connect, it will report a protocol mismatch and exit (if the listener isn't a web service). If curl cannot connect, it will time out.

For example, port 5672 on host is either closed or blocked by a firewall:

$ curl
curl: (7) couldn't connect to host

However, from a different system, port 5672 on host can be reached, and appears to be running an AMQP listener.

$ curl
curl: (56) Failure when receiving data from the peer

It's important to distinguish between the different messages: the first failure was because curl could not connect to the port. The second failure is a success test, though curl expected an HTTP listener instead of an AMQP listener.

share|improve this answer
If curl isn't available, wget might be. wget -qS -O- http://ip.add.re.ss:port should effectively do the same thing. –  Michael Kjörling Jul 19 '13 at 17:52
This even works with a hostname, ex. curl myhost:22. –  에이바 Feb 25 '14 at 16:17
This may be incorrect. I am havng a tomcat service running, but getting 404 error. # curl -k <html><head><title>Apache Tomcat/7.0.34 - Error report</title><style><!--H1 --- HR {color : #525D76;}--></style> </head><body><h1>HTTP Status 404 - /</h1><HR size="1" noshade="noshade"><p><b>type</b> Status report</p><p><b>message</b> <u>/</u></p><p><b>description</b> <u>The requested resource is not available.</u></p><HR size="1" noshade="noshade"><h3>Apache Tomcat/7.0.34</h3></body></html> –  Mohammad Shahid Siddiqui Jun 2 at 6:30

The simplest method, without making use of another tool, such as socat, is as described in @lornix's answer above. This is just to add an actual example of how one would make use of the psuedo-device /dev/tcp/... within Bash. if you wanted to say test if another server had a given port accessible via the command line.


Say I have a host on my network named skinner.

$ (echo > /dev/tcp/skinner/22) >/dev/null 2>&1 \
    && echo "It's up" || echo "It's down"
It's up

$ (echo > /dev/tcp/skinner/222) >/dev/null 2>&1 && \
    echo "It's up" || echo "It's down"
It's down

The reason you want to wrap the echo > /dev/... in parens likes this, (echo > /dev/...) is because if you don't, then with tests of connections that are down, you'll get these types of messages showing up.

$ (echo > /dev/tcp/skinner/223) && echo hi
bash: connect: Connection refused
bash: /dev/tcp/skinner/223: Connection refused

These can't simply be redirected to /dev/null since they're coming from the attempt to write out data to the device /dev/tcp. So we capture all that output within a sub-command, i.e. (...cmds...) and redirect the output of the sub-command.

share|improve this answer
This is excellent. Wish it would get voted up to the top. I only read this far down the page because I accidentally scrolled before closing it. –  Okuma.Tony Feb 12 at 13:44
@Okuma.Tony - yes that's always an issue with Q's that have many answers 8-). Thanks for the feedback though, it's appreciated. –  slm Feb 12 at 14:26

It shouldn't be available on your box but have you tried with nmap?

share|improve this answer
nmap is a good tool, but not available on these systems. Rather than download nmap, compile it, install it to my home directory, then copy it to all the other systems, I was hoping to find a way using existing tools available in most Linux installations. –  Steve HHH Jul 19 '13 at 17:16
[admin@automation-server 1.2.2]# nc -v -z -w2 6443
nc: connect to port 6443 (tcp) failed: Connection refused

[admin@automation-server 1.2.2]# nc -v -z -w2 6443
Connection to 6443 port [tcp/sun-sr-https] succeeded!

Hope it solves your problem :)

share|improve this answer

Your Answer


By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.