18 marzo, 2016

Portknocking para asegurar el servicio SSH

Retomo este blog para publicar, en este caso, la configuración que he puesto en marcha de este sistema de protección de forma que me sea fácil volver a ella para cada servidor que administre. Está basado en la publicada en https://www.digitalocean.com/community/tutorials/how-to-use-port-knocking-to-hide-your-ssh-daemon-from-attackers-on-ubuntu y abundan las entradas por la web de configuraciones similares.
No voy a profundizar en la técnica del portknocking ni en la necesidad de securizar un servidor, de esto también abunda la información en la red. Lo básico que hay que saber es que el puerto del servicio SSH debe estar abierto y público para poder hacer la conexión remotamente y esto hace que sea susceptible a múltiples ataques, principalmente de fuerza bruta.
Existen muchas técnicas de protección y como propone la idea de las capas de la cebolla en esto de la seguridad, lo recomendable es que ésta sea una capa más y se complemente con otras como denyhost, fail2ban, etc...
Éstas técnicas utilizan en su mayoría el firewall integrado en las distintas distribuciones GNU/Linux y más concretamente en Debian que es mi caso por lo que primero vamos a tratar el tema del cortafuegos, pieza imprescindible en la seguridad de nuestros servidores.

 

IPTABLES

Lo ideal según la teoría de la seguridad es configurar el cortafuegos de forma que bloquee todas las conexiones a nuestro servidor por defecto y configurar que acepte aquellos puertos/tráfico que nos interese de forma concreta. En este caso (para este servidor en particular), voy a bloquear únicamente el tráfico SSH, con los comandos:

iptables -I INPUT 1 -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT iptables -I INPUT 2 -p tcp --dport 22 -j DROP

Explico:

Con el primero me aseguro que las conexiones ya establecidas (por ejemplo la actual si estamos accediendo al servidor por SSH) se mantienen abiertas y con el segundo bloqueo todo el tráfico SSH. En ambos casos no añado las líneas al firewall actual sino que las inserto (-I) en la posición 1 y 2 de la cadena INPUT para que prevalezcan a las reglas actuales del firewall. En mi caso mantengo a continuación las reglas que crea el fail2ban, por ejemplo, de forma que si alguna vez me quedase el puerto abierto aún tendría esta otra línea de defensa.


KNOCKD

Este es el servicio que nos va a permitir abrir el firewall para el SSH bajo petición, se basa en la idea de escuchar las conexiones entrantes y si se produce una secuencia concreta, envía el comando adecuado para abrir la puerta.
Instalamos el servicio (en debian y como root) con:

aptitude install knockd

o el sistema que más os guste para ello (apt-get, etc...) y editamos el fichero de configuración en /etc/knockd.conf que por defecto viene así:


[options] UseSyslog [openSSH] sequence = 7000,8000,9000 seq_timeout = 5 command = /sbin/iptables -A INPUT -s %IP% -p tcp --dport 22 -j ACCEPT tcpflags = syn [closeSSH] sequence = 9000,8000,7000 seq_timeout = 5 command = /sbin/iptables -D INPUT -s %IP% -p tcp --dport 22 -j ACCEPT tcpflags = syn

Evidentemente por motivos de seguridad no podemos dejar esta configuración, en mi caso he optado por esta otra:

[options] # UseSyslog LogFile = /var/log/knockd.log [SSH] sequence = 666,9663:udp,2355 seq_timeout = 5 command = /sbin/iptables -I INPUT 1 -s %IP% -p tcp --dport 22 -j ACCEPT tcpflags = syn cmd_timeout = 30 stop_command = /sbin/iptables -D INPUT -s %IP% -p tcp --dport 22 -j ACCEPT [OpenSSH] sequence = 789:udp,456:udp,852:udp,951:udp seq_timeout = 5 command = /opt/scripts/ssh_open.sh tcpflags = syn cmd_timeout = 60 stop_command = /opt/scripts/ssh_close.sh

Como es lógico, estos puertos no son los que uso realmente, explico los cambios:
En lugar de usar el fichero de log de sistema (UseSysLog) le especifico un fichero de log independiente. Al menos inicialmente viene bien para comprobar que está funcionando correctamente.
En la secuencia SSH le pongo tres puertos (en este caso dos TCP, la conexión por defecto y uno UDP, 5 segundos de espera máxima entre cada conexión y el comando de apertura, el que se ejecutará si la secuencia es correcta. En este caso, añado al iptables la IP desde la que hago la petición para que le abra el puerto (sólo a esta IP). A los 30 segundos se lanza el otro comando de iptables que borra la regla añadida anteriormente. Con esto no perdemos la conexión establecida gracias a la regla de iptables que habíamos añadido en la sección anterior, de forma que ya no quedará abierto el puerto para esta IP y en cuanto nos desconectemos todo volverá a estar cerradito.
Con esto bastaría pero yo he añadido otra secuencia más en OpenSSH para lanzar un script que abre el SSH del todo y a los 60 segundos lo vuelve a cerrar con otro script. Porqué? Pues en algunos entornos no he sido capaz de que me funcione la primera secuencia, seguramente por limitaciones propias de la red en la que envío la petición (red securizada que puede tener alguna protección para los envíos de paquetes) y lo que he tenido que hacer es recurrir a esta otra secuencia que me permite abrir el puerto 22 desde el móvil y me da 60 segundos para conectarme antes de volver a cerrarlo. Llamemoslo una apertura de emergencia.

Para activar el servicio es imprescindible editar el fichero /etc/default/knockd y modificar la linea:

START_KNOCKD=1

con un 1 en lugar del 0 que viene por defecto, con esto le indicamos al servicio que se inicie con el sistema.

En este fichero también aparece la línea:

#KNOCKD_OPTS="-i eth1"

que en algunos casos debemos descomentar e indicar en qué interfaz ha de escuchar las peticiones. Por ejemplo, en algunos VPS la interfaz es virtual y puede tener una nomenclatura diferente o usar una subinterfaz.

Una vez modificado estos ficheros debemos reiniciar el servicio, por ejemplo:

service knockd restart

y comprobar en el fichero de log que detecta las peticiones, por ejemplo con:

tail -f /var/log/knockd.log

La llamada

Para hacer "la llamada" y activar el puerto 22, solo tenemos que enviar desde la máquina cliente la secuencia configurada anteriormente. Hay diversas formas de hacerlo pero la más sencilla sin duda es usar el propio knockd (habrá que instalarlo también en esta máquina) que permite usar el comando "knock" para hacer las peticiones. En este caso concreto sería:

knock servidor 666 9663:udp 2355 && ssh usuario@servidor

como se puede ver, hay que especificar el nombre del servidor (o la IP) y luego la secuencia de puertos (por defecto TCP y se puede especificar si hay alguno UDP como en el segundo del ejemplo). En este caso para ahorrar tiempo le añado a continuación la conexión por ssh, si todo va bien, ya permitirá conectarse.

El resultado en el fichero de log del servidor sería algo parecido a esto:

[2016-03-18 12:55] 51.127.41.17: SSH: Stage 1 [2016-03-18 12:55] 51.127.41.17: SSH: Stage 2 [2016-03-18 12:55] 51.127.41.17: SSH: Stage 3 [2016-03-18 12:55] 51.127.41.17: SSH: OPEN SESAME [2016-03-18 12:55] SSH: running command: /sbin/iptables -I INPUT 1 -s 51.127.41.17 -p tcp --dport 22 -j ACCEPT [2016-03-18 12:56] 51.127.41.17: SSH: command timeout [2016-03-18 12:56] SSH: running command: /sbin/iptables -D INPUT -s 51.127.41.17 -p tcp --dport 22 -j ACCEPT

Hay multiples aplicaciones que permiten hacer el port-knocking, yo he probado varias en Android y funcionan bien, espero que os sirva de algo.

02 diciembre, 2009

Manifiesto “En defensa de los derechos fundamentales en internet”

Ante la inclusión en el Anteproyecto de Ley de Economía sostenible de modificaciones legislativas que afectan al libre ejercicio de las libertades de expresión, información y el derecho de acceso a la cultura a través de Internet, los periodistas, bloggers, usuarios, profesionales y creadores de internet manifestamos nuestra firme oposición al proyecto, y declaramos que…

  1. Los derechos de autor no pueden situarse por encima de los derechos fundamentales de los ciudadanos, como el derecho a la privacidad, a la seguridad, a la presunción de inocencia, a la tutela judicial efectiva y a la libertad de expresión.
  2. La suspensión de derechos fundamentales es y debe seguir siendo competencia exclusiva del poder judicial. Ni un cierre sin sentencia. Este anteproyecto, en contra de lo establecido en el artículo 20.5 de la Constitución, pone en manos de un órgano no judicial -un organismo dependiente del ministerio de Cultura-, la potestad de impedir a los ciudadanos españoles el acceso a cualquier página web.
  3. La nueva legislación creará inseguridad jurídica en todo el sector tecnológico español, perjudicando uno de los pocos campos de desarrollo y futuro de nuestra economía, entorpeciendo la creación de empresas, introduciendo trabas a la libre competencia y ralentizando su proyección internacional.
  4. La nueva legislación propuesta amenaza a los nuevos creadores y entorpece la creación cultural. Con Internet y los sucesivos avances tecnológicos se ha democratizado extraordinariamente la creación y emisión de contenidos de todo tipo, que ya no provienen prevalentemente de las industrias culturales tradicionales, sino de multitud de fuentes diferentes.
  5. Los autores, como todos los trabajadores, tienen derecho a vivir de su trabajo con nuevas ideas creativas, modelos de negocio y actividades asociadas a sus creaciones. Intentar sostener con cambios legislativos a una industria obsoleta que no sabe adaptarse a este nuevo entorno no es ni justo ni realista. Si su modelo de negocio se basaba en el control de las copias de las obras y en Internet no es posible sin vulnerar derechos fundamentales, deberían buscar otro modelo.
  6. Consideramos que las industrias culturales necesitan para sobrevivir alternativas modernas, eficaces, creíbles y asequibles y que se adecuen a los nuevos usos sociales, en lugar de limitaciones tan desproporcionadas como ineficaces para el fin que dicen perseguir.
  7. Internet debe funcionar de forma libre y sin interferencias políticas auspiciadas por sectores que pretenden perpetuar obsoletos modelos de negocio e imposibilitar que el saber humano siga siendo libre.
  8. Exigimos que el Gobierno garantice por ley la neutralidad de la Red en España, ante cualquier presión que pueda producirse, como marco para el desarrollo de una economía sostenible y realista de cara al futuro.
  9. Proponemos una verdadera reforma del derecho de propiedad intelectual orientada a su fin: devolver a la sociedad el conocimiento, promover el dominio público y limitar los abusos de las entidades gestoras.
  10. En democracia las leyes y sus modificaciones deben aprobarse tras el oportuno debate público y habiendo consultado previamente a todas las partes implicadas. No es de recibo que se realicen cambios legislativos que afectan a derechos fundamentales en una ley no orgánica y que versa sobre otra materia.

Este texto se publica multitud de sitios web. Si estás de acuerdo, publícalo también en tu blog.


20 marzo, 2009

Resumen semanal (12/2009)

En esta ocasión he configurado el acceso automático por SSH a mi server desde el portátil siguiendo uno de los muchos tutoriales al respecto que se pueden encontrar por la red. Concretamente este que visto en el blog de mi amigo apermuy. Es fácil de hacer pero he detectado un pequeño problema para el que no he encontrado una solución satisfactoria.

El problema concreto es con un script que automatiza el proceso de copia de la clave publica (una vez generada con 'ssh-keygen -t rsa') que se ejecuta con 'ssh-copy-id'.

Este útil script no tiene en cuenta la posibilidad de que el sshd se haya configurado con otro puerto que no sea el 22 (por defecto). Tanto el sshd como muchos servicios que lo usan (scp, unison, etc...) permiten usar otro puerto que no sea el 22 (recomendable por motivos de seguridad) y que en mi caso es el 2002 (es mentira, pero para el caso da igual).

Esto implica que al conectarse al server hay que especificar el puerto de esta manera:
'ssh usuario@10.0.0.1 -p 2002'

Hasta aquí todo correcto pero el script en cuestión (ssh-copy-id) no tiene ningún parámetro (o yo no lo he encontrado) para hacer este copiado correctamente usando un puerto concreto, por lo que quién (como yo) tenga un puerto diferente tiene que hacer el copiado a mano, cosa que por otra parte no es nada del otro mundo.

En fin, que desde aquí reto a mi amigo apermuy que complete este scripts demostrando sus dominios del shell scripting.

Y enlaces que recomiendo de esta semana: