CWKPF Cuasi-Web Knocking para Packet Filter

Click here to read this in English. But do it under your own risk, because my English is just horrible (corrections are welcome).

El problema

Suele pasarme, como a muchos, de tener múltiples servidores en una única IP pública. Para administrarlos mi herramienta favorita es SSH, por lo que solía redireccionar puertos no-estándares a los correspondientes 22/tcp de cada máquina. Por ejemplo, el puerto 22 en la interfaz pública es para el firewall, el 222 para el webserver, el 2222 para el servidor de base de datos.

El problema es que, mucha veces, me conecto desde redes restrictivas, donde algunos de estos puertos está cerrados. Por lo que empezaba a saltar de máquina en máquina, teniendo que recordar contraseña y soportando el delay.

Sumando a esto está el problema de los bruteforcers que constantemente amenazan y molestan a nuestros servidores SSH.

El enfoque

Fue por esto que decidí escribir un cuasi-web knocking para Packet Filter (OpenBSD), mi sistema firewall preferido. La idea es simple. El firewall tiene una página web que, al ser navegada de una forma particular, redirecciona el puerto 22/tcp a distintas máquinas de forma que solo la IP que navegó dicha página tenga acceso.

Premisas, en orden de importancia:

  • Simplicidad. Debe ser fácil de navegar la página con telnet o netcat si llegase a faltar un browser.
  • Seguridad. No sacar el Apache de OpenBSD de su jaula chroot. Generar la redirección debe tener alguna (aunque simple) forma de autenticación.
  • Eficiencia. Los procesos deben ser livianos (mi firewall tiene cosas más importantes que hacer).

    Aviso: No estoy seguro de haber cumplido con estas premisas, así que acepto sugerencias. Esto de meter un shell y netcat dentro de un chroot me da como mala espina. Hagas lo que hagas, es tu responsabilidad.

    Requerimientos:

  • bash y mod_fastcgi, para que corra el script webknock.sh (y su archivo de configuración, secret).
  • python, para que corra el script pfctl.py.
    Todo estos son paquetes precompilados que pueden bajarse desde su repositorio oficial favorito de OpenBSD.

    Instalación:

  • Dentro del chroot de Apache
    El componente principal es webknock.sh, una pagina cgi que será el webknock en cuestión y que se ubicará acá: /var/www/cgi-bin/webknock.sh
    Esta página es configurable desde /var/www/conf/webknock/secret. El directorio /var/www/conf/webknock debe tener permisos de escritura para el usuario www o aquel usuario con el que corra Apache.

    El archivo webknock.sh es un script de bash que requiere comandos complementarios dentro del chroot para funcionar. Por lo que deben ser copiados dentro de la siguiente estructura:

    /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
    
    Las bibliotecas pueden variar según la versión del sistema operativo. El comando ldd <binario> te ayudará a saber que bibliotecas copiar dentro del chroot.
    Apache (quien ya tiene el modulo de fastcgi instalado) debe ser configurado de la siguiente manera:
    ScriptAlias /knock "/var/www/cgi-bin/webknock.sh"
    <Directory "/var/www/cgi-bin/*">
        AllowOverride None
        Options None
        Order allow,deny
        Allow from all
    </Directory>
    
  • Fuera del chroot de Apache
    Packet filter debe ser configurado para redireccionar el puerto de SSH. Para ello se utlizan tables, que leeran un IP de origen desde /var/www/conf/webknock/orig y le rediccionaran el puerto 22/tcp al host que figure en /var/www/conf/webknock/dest. Con este fin, la configuración en /etc/pf.conf es la siguiente (la interfaz externa es $ext_if).
    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>
    
    El script pfctl.py es un pequeño daemon escrito en Python que escucha en el puerto 50150 de localhost. Su función es sencilla: cada vez que recibe una conexión, corre el comando pfctl -Tl -f /etc/pf.conf. El script webknock.sh se conectará cada vez que requiera que se recarguen las tablas ssh_orig y ssh_dest.

    pfctl.py puede copiarse en /usr/local/sbin/pfctl.py. Para que corra cada vez que se inicia el sistema, en /etc/rc.local se debe incluir:

    if [ -x /usr/local/sbin/pfctl.py ]; then
                 echo -n ' pfctl.py';       /usr/local/sbin/pfctl.py &
    fi
    

    Uso:
    El webknocking estará accesible desde http:\\[sitio_com]\knock. Para producir algun cambio en la redirección del firewall se puede acceder a los links o directamente a http://[sitio_com]/knock?[password]=[action].

  • Dentro del chroot de Apache

    El autor y la licencia

    El autor es Luciano Bello, quien está deseoso de recibir sus consultas, mejoras, sugerencias y errores encontrados a luciano [en] linux [punto] org [punto] ar. Los scripts webknock.sh y pfctl.py estan escritos bajo DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE © 2008 Luciano Bello.


    Last update: Sat, 01 Mar 2008 19:15:02 -0200