Many people, like myself usually have many servers hidden behind a single public IP address. To administrate them, my favorite tool is SSH; that is why I used to redirect non-standard ports to the 22/tcp of every machine. For example, the 22/tcp port of the public interface is my firewall, the 222 is the webserver and the 2222 is the database one.
The problem is that many times I meet to connect to those from restricted networks where some of those ports are closed. Then I had to hop from machine to machine having to remember the password and put up with the delay.
There is also the problem of the bruteforcing attacks that are a constant threat and nuisance to our SSH servers
So, I decided to write this cuasi-web knocking for OpenBSD's
Packet Filter, my firewall of choise. The idea is simple, the firewall is hosting a simple web page that when surfed in a particular way,
redirects the 22/tcp port to different hosts such as only the IP that
surfed this web page has access
Guidelines, in order of importance:
| Notice: I'm not sure I fullfilled all the requirements, so I'm open to any suggestions. This thing about a shell and netcat inside a chroot jail feels hackish. In any case, whatever you do is your responsibility. |
Requirement:
Installation:
webknock.sh is a bash script that requires some extra commands inside the chroot to work, those must be copied there following the this structure:
/var/www/
|-- bin
| |-- cat
| `-- echo
`-- usr
|-- bin
| |-- cut
| |-- grep
| `-- nc
|-- lib
| |-- libc.so.30.3
| |-- libc.so.38.2
| |-- libtermcap.so.9.0
| `-- libz.so.4.1
|-- libexec
| `-- ld.so
`-- local
`-- bin
`-- bash
The library versions can change depending on the version of the SO.
The ldd <binary> command will let you know what the right libraries are.
ScriptAlias /knock "/var/www/cgi-bin/webknock.sh"
<Directory "/var/www/cgi-bin/*">
AllowOverride None
Options None
Order allow,deny
Allow from all
</Directory>
table <ssh_orig> persist file "/var/www/conf/webknock/orig" table <ssh_dest> persist file "/var/www/conf/webknock/dest" rdr pass on $ext_if proto tcp from <ssh_orig> to ($ext_if) port 22 -> <ssh_dest>The pfctl.py script is a small daemon written in Python that listens in the 50150 port in the loopback interface. It's purpose is simple: each time it receives a connection, it will run the pfctl -Tl /etc/pf.conf command. webknock.sh will trigger this event every time the ssh_orig and ssh_dest tables need to be reloaded.
pfctl.py should be copied to /usr/local/sbin/pfctl.py. To run it every time the system starts, you must include the following inside /etc/rc.local:
if [ -x /usr/local/sbin/pfctl.py ]; then
echo -n ' pfctl.py'; /usr/local/sbin/pfctl.py &
fi
Usage:
The webknocking will be accessible in http:\\[your_site_com]\knock. To make any change in the firewall redirection you can access to the links or directly to http://[your_site_com]/knock?[your_password]=[action].