In the field of IT systems security, concept of”
port knocking” is relatively new. However with the passage of time, it is getting popular day by day among system and security administrators.
Port knocking is a method of externally opening ports on a firewall by generating a connection attempt on a set of pre-specified closed ports. Once a correct sequence of connection attempts is received, the firewall rules are dynamically modified to allow the host which sent the connection attempts to connect over specified port (s).
The primary purpose of
port knocking is to prevent an attacker from scanning a system for potentially exploitable services by doing a port scan. Until the correct knock sequence is used, the protected ports will appear closed– so attackers won’t be able to conduct an attack on those ports.
More specifically,
Port knocking works on the concept that users wishing to attach to a network service must initiate a predetermined sequence of port connections or send a unique string of bytes before the remote client can connect to the eventual service.
For example, suppose that a remote client wants to connect to an FTP server. The administrator configures the port-knocking requirements ahead of time, requiring that connecting remote clients first connect to ports 2000, 4000, and 7107 before connecting to the final destination port, 21 on FTP server.
The administrator tells all legitimate clients about the correct” combination” of knocks to port knocking daemon running on FTP server and hence when they want to connect to FTP service, they simply send these knocks to the server and then start using FTP service.
The question arises, what is the basic advantage of the additional step of sending knocks and then connecting to FTP service? The answer is simple: The FTP service is not always running on the server, it will be started only when the correct port knocks are sent to server, and it will shut down once it receives another predefined sequence of port knocks.
The potential backdoor to business-critical services is only to be opened for a short time, when it’s required. Once the service is no longer needed, it is closed again, mitigating the vulnerability to attack.
One of the primary advantages to using
port knocking is that it is platform, service, and application agnostic. Any operating system with the correct client and server software can take advantage of port knocking. If you need help finding a tool, you can find a list of port knocking implementations
here. The site lists clients and daemons for pretty much any platform you’d care to use.
I selected
knockd
, which is considered to be one of the most famous and robust implementation of port knocking mechanism for
Linux and UNIX. In this article, I will cover setting up port knocking on a Red Hat Enterprise Linux (RHEL) server, using
knockd
, a popular open source port knocking tool. Most importantly, I will try to extend the idea of port knocking beyond simple firewall modifications to more complex system administration tasks.
Note that
knockd
is available for other systems as well, so if you’re using Debian, Ubuntu, Mac OS X, or even Windows, you should be able to follow along with most of the advice herein to secure your system with
knockd
.
Flaws with Port Knocking
Before we begin, I should note that port knocking has some detractors. Some IT security professionals say that a predefined and fixed sequence of knocks is, in and of itself, a security flaw. To overcome this, some port knocker daemons have been modified to generate a random sequence of knocks, which can be used by clients to issue requests.
It’s also important to remember that port knocking is just one component of a successful security strategy. You’ll need to deploy other security mechanisms so that if an attacker is successful in providing the correct sequence, they are still faced with authentication and other barricades before connecting to a service.
Port Knocking: A Basic Overview
To start, let’s take a look at the basic functionality of a port knock server.
knockd
is a daemon that runs on a server, passively listening to network traffic. You configure
knockd
with a sequence of ports, the length of time between connection attempts, the type of packet that will be sent, and the command to be run when the correct sequence is given.
Once
knockd
” sees” a port sequence it has been configured to recognize, it will run the command it’s been configured to run. Note that you can use TCP, UDP, or a combination of both. Usually the action will be an
iptables
command, but not always.
So, to implement port knocking, we start with the installation of
knockd
and run it in the background. (Or foreground, if you wish, but we will usually want to run it in the background.)
Securing A MySQL Database Remote Connections with Port Knocks
Now that we know what port knocking is, let’s put it to use. In this scenario, I have a business-critical MySQL-based application running on RHEL. On occasion, I need to allow remote connections from a DBA who is performing basic database maintenance activities.
However, for security reasons, we don’t want to allow remote database connections at all times or from every IP address. Because we wanted tighter control over remote connections, we decided to explore port knocking so that remote connections would be open for a limited time only and from a specific IP address.
Let’s start with the firewall rule, just in case you’re not already a firewall wizard. To append a rule to one of the” chains,” you’ll use the
-A
option. The
-I
parameter tells
iptables
to insert the rule into a specific position in the chain. This is important because you may want specific rules to be processed first. Make sure you give it a rule number.
Now, to secure MySQL connections to my database server (172.16.2.183), I blocked network traffic on server’s MySQL port (default 3306) coming from all addresses. For this purpose, I executed following command:
iptables -A INPUT -p tcp -s 0/0 -d 172.16.2.183 --dport 3306 -j REJECT
You don’t want to be reissuing the command every time you restart the machine, so you’ll want to save the rule permanently, using
iptables-save
.
Getting and configuring knockd
The next step is to install the
knockd
server on the system you want to use it on. You can get the RPM from the RHEL network.
After installing
knockd
it’s time to customize your configuration. The
knockd
config file is found at
/etc/knockd.conf
[options]
logfile=/var/log/knockd.log
[DB2clientopen]
sequence = 7050,8050,9050
seq_timeout = 10
tcpflags = syn
command = /sbin/iptables -I INPUT 1 -p tcp -s 192.168.2.201
--sport 1024:65535 -d 172.16.2.183 --dport 3306 -m state
--state NEW,ESTABLISHED -j ACCEPT
[DB2clientclose]
sequence = 9050,8050,7000
seq_timeout = 10
tcpflags = syn
command = /sbin/iptables -D INPUT 1
Let’s take a look at the format. The syntax is very simple, you give
knockd
option / value pairs, separated by
=
, and port numbers are separated by commas in the order you want the” knocks” to be received. Don’t forget to specify a logfile, you may need to review it later!
It should be obvious from the
knockd.conf example that it has two types of actions that can be executed by the daemon, depending on the sequence it receives.
First, if it receives syn packets to port 7050, 8050, and 9050,
knockd
will insert the first iptables rule as rule number 1 in the
INPUT
chain. This will open the MySQL database port, so a remote connection can be made from
192.168.2.201– and only that IP address. It’s a good idea to specify the IP address whenever possible, so that if an attacker tries to connect while the port is open, they will still be denied.
On the other hand, if the server receives a knock sequence of 9050, 8050, and 7000, it will delete the rule so that all remote database connections will be closed down again.
I made sure that MySQL would know what address my DBA would be coming from, so I added my PC’s IP address to the server’s
/etc/hosts file and created a test database called
test1, and created a user called test1 as well with the appropriate grant privileges.
First, fire up the MySQL client with
mysql-u root-p test1
and enter the following commands:
mysql> create user test;
mysql> grant all privileges on *.* to 'test@dbawin'
identified by 'polanipass' with grant option;
Next, restart
knockd
as a daemon.
/usr/sbin/knockd -d
It should be noted that, by default,
knockd
will start listening on
eth0. If you need it to run on a different interface, you can configure it to do so using the
-i
option. For instance, to start
knockd
as a daemon on
wlan0 you’d use
/usr/sbin/knockd-i wlan0
. If you’re always going to run
knockd
on a different interface, you can add this to your
knockd.conf:
[options]
interface = wlan0
Knock, Knock, It’s Me!
Now,
knockd
isn’t very useful without a client, so let’s get a client to talk to
knockd
. I chose a Windows-based Cygwin client, but you can find a client for just about any client OS at the implementations page mentioned earlier.
To use the Windows client, you open a DOS prompt and run something similar to this command:
C:KNOCKKNOCKWINDOWS>knock.exe 172.16.2.183 9050 8050 7000
Of course, the IP address and ports will vary. Once the” knock” is issued, the knock daemon will execute the iptables command listed under the
[DB2clientopen]
section of knockd.conf and add the rule in INPUT chain to allow DB2 PC to connect to database running on server.
Now you can connect to your MySQL database with your favorite client and do whatever you need to do. Once you’re finished, it’s time to close the door.
If you send the close knock sequence, in this case a
syn
packet sent to ports 9050, 8050, and then 7000, the MySQL port will be closed and all connections will be terminated. If you try to reconnect to the server, your MySQL client will time out and you’ll eventually see an access error. This will be the case until you send the proper sequence to re-open the port.
So, now you see how you can use port knocking to increase security for remote MySQL connections. Of course, this is really database (and application) independent, so you can use port knocking to secure any database or application you want to connect to remotely.
If it’s too much hassle to open and close the connection each time you need to connect to the database, it might make more sense to set it up so that the port is open during specific hours. For example, if your database guru works 10 a.m. to 7 p.m., you could set up a script to open the port a bit before 10 a.m., and close the port a bit after 7 p.m.
This is not quite as secure, but it does mean that the port won’t be open 24/7, so it may block some automated and casual (i.e., not targeted) attacks. Also, if the port knocking is coupled with only allowing connections from specific IP addresses or IP address ranges, then you have an additional layer of security.
Performing Other System Administration Tasks with Knocks
But wait, that’s not all! Port knocking can be used to do more than set iptables rules. After configuring
knockd
to play doorkeeper, I decided to explore the feature and see if I could use it to make my life easier in other ways.
I decided I wanted to be able to restart my system remotely, just by” knocking” in the right sequence. I also configured
knockd
to kick off my backups to tape, so I don’t even need to log in to start the backup– just send a quick series of packets, and my data is safe another day.
Here’s my
/etc/knockd.conf:
[options]
logfile=/var/log/knockd.log
[systemreboot]
sequence = 7050,8050,9050
seq_timeout = 10
tcpflags = syn
command = /usr/bin/reboot
[systembackup]
sequence = 9050,8050,7000
seq_timeout = 10
tcpflags = syn
command = /usr/bin/tar -cf /dev/rmt0 /home/root/
You can take this a lot farther, and set it up so that other admins (say, the junior admin who’s reliable but still a bit green) can perform complex actions just by using a knock client, or even just by running a shell script that sends the packets.
Summary
Port knocking is a very useful tool for systems security. It is because of its usefulness and robustness that the number of implementations, and users, are growing rapidly. If you can open a door into a closed black box for to perform some system administration tasks, even without requiring a login to the system, it can be very ideal for many environments.
Finally, it is always a good idea to further secure your systems by changing the knock sequences frequently, or by using random seed generators to create random port knocks.