Implementar nuestra propia VPN con OpenVPN en Debian

Razones para montar un servidor VPN hay muchas. En mi caso es simple: por mi trabajo me toca viajar y estar lejos de casa muy seguido por lo que necesito acceder a mi red para realizar distintas tareas que requieren que mis equipos se vean unos a otros como si estuvieran conectados a la misma LAN, todo siempre de la manera más segura posible. Si bien es cierto que muchas de esas tareas las realizo sobre SSH, hay otras que prefiero hacerlas a través de un servicio VPN.

Esta entrada está enfocada en cómo implementar este tipo de servidores usando OpenVPN en una distribución Debian. Para tales fines, se puede montar un servidor utilizando un equipo antiguo que ya no utilices, o bien, disponer de algún dispositivo tipo RaspberryPI.

No hace falta aclarar que necesitamos una ip pública fija o en caso contrario, usar un servicio tipo NoIP para acceder al servidor desde fuera de la LAN. Para no extenderme demasiado, voy a pasar por alto los detalles sobre esto y voy a ir directamente al grano.

Instalación y configuraciones iniciales

Instalamos el servidor, las herramientas de administración de certificados y ufw para simplificar las configuraciones del firewall.

$ sudo apt update && apt install openvpn easy-rsa ufw

Posteriormente, vamos a descomprimir y copiar el archivo de configuración de ejemplo que viene con la documentación de openvpn al directorio correspondiente para luego editarlo.

$ sudo gunzip -c /usr/share/doc/openvpn/examples/sample-config-files/server.conf.gz > /etc/openvpn/server.conf

$ sudo nano /etc/openvpn/server.conf

/etc/openvpn/server.conf

[…]
# Puerto para las conexiones VPN. Por defecto 1194
port 1194
[…]
# Protocolo a utilizar
;proto udp
proto tcp
[…]
# Tipo de túnel
# TUN emula un dispositivo punto a punto
# TAP simula una interfaz ethernet (bridge o puente)

;dev tun
dev tap
[…]
# Bits de las claves RSA
dh dh2048.pem
[…]
# Redirigir el tráfico web hacia el destino que corresponda
push “redirect-gateway local def1 bypass-dhcp”
[…]
# Configuración de los DNS
push “dhcp-option DNS 208.67.222.222”
push “dhcp-option DNS 208.67.220.220”
[…]
# Permisos de usuarios y grupos
user nobody
group nogroup
[…]

Ahora bien, debemos avisarle al sistema que todo el trafico proveniente desde los clientes tiene que continuar su camino hacia la Internet, de lo contrario, el tráfico se detendría en el servidor. Para esto, ejecutamos:

$ sudo echo 1 > /proc/sys/net/ipv4/ip_forward

$ sudo nano /etc/sysctl.conf

/etc/sysctl.conf

[…]
net.ipv4.ip_forward=1
[…]

Además de ejecutar el comando, editamos el archivo /etc/sysctl.conf para que esta configuración sea persistente, es decir, resistente a reinicios.

 

Configurar el firewall

Como ya mencioné, usaremos ufw para simplificar la administración del firewall para nuestra VPN. Lo primero será abrir el puerto y protocolos respectivos por dónde transitarán los paquetes y luego vamos a permitir el tráfico SSH, básicamente para poder acceder al servidor cuando lo necesitemos (recordemos que el servidor está en un equipo que no necesariamente tiene un monitor conectado).

$ sudo ufw allow ssh

$ sudo ufw allow 1194/udp

Establecemos las políticas y reglas en el firewall.

$ sudo nano /etc/default/ufw

/etc/default/ufw

[…]
DEFAULT_FORWARD_POLICY=”ACCEPT”
[…]

$ sudo nano /etc/ufw/before.rules

/etc/ufw/before.rules

[…]
#
# rules.before
#
# Rules that should be run before the ufw command line added rules. Custom
# rules should be added to one of these chains:
# ufw-before-input
# ufw-before-output
# ufw-before-forward
#
# START OPENVPN RULES
# NAT table rules
*nat
:POSTROUTING ACCEPT [0:0]
# Allow traffic from OpenVPN client to eth0
-A POSTROUTING -s 10.8.0.0/8 -o eth0 -j MASQUERADE
COMMIT
# END OPENVPN RULES
#
# Don’t delete these required lines, otherwise there will be errors
*filter
[…]

Finalmente, activamos el firewall

$ sudo ufw enable

 

Crear y configurar la autoridad certificadora (CA), los certificados (crt) y las claves (rsa-keys)

El paquete easy-rsa provee varios scripts que facilitan la tarea de crear y configurar los certificados y claves de identificación cliente-servidor

Copiamos los scripts predefinidos del paquete easy-rsa al directorio /etc/openvpn. Luego creamos el directorio /etc/openvpn/easy-rsa/keys donde se almacenarán los certificados y claves.

$ sudo cp -r /usr/share/easy-rsa/ /etc/openvpn

$ sudo mkdir /etc/openvpn/easy-rsa/keys

Editamos el archivo que contiene la información requerida para crear la autoridad certificadora. Los datos de país, ciudad, nombre y correos de la compañía, etcétera podemos completarlos con cualquier valor que deseemos. La clave (KEY_NAME) la llamaremos server para simplificar su uso e identificarla como la clave del servidor fácilmente.

$ sudo nano /etc/openvpn/easy-rsa/vars

/etc/openvpn/easy-rsa/vars

[…]
export KEY_COUNTRY=”US”
export KEY_PROVINCE=”TX”
export KEY_CITY=”Dallas”
export KEY_ORG=”My Company Name”
export KEY_EMAIL=”sammy@example.com”
export KEY_OU=”MYOrganizationalUnit”
[…]
export KEY_NAME=”server”
[…]

Generamos los parámetros Diffie-Hellman con el comando:

$ sudo openssl dhparam -out /etc/openvpn/dh2048.pem 2048

Cambiamos la sesión de la consola para trabajar como root. Nos movemos al directorio donde se encuentran los scripts e iniciamos la infraestructura de claves (PKI).

$ su -
Contraseña:

# cd /etc/openvpn/easy-rsa

# . ./vars

Limpiamos las claves que hayan sido generadas previamente y que ya no se usan, construimos el certificado y la clave del servidor.

# ./clean-all

# ./build-ca

# ./build-key-server server
El último comando descrito creará los archivos ca.crt, server.crt y server.key y los alojará en el directorio /etc/openvpn/easy-rsa/keys.

Ahora, volveremos al archivo de configuración del servidor para configurar la ruta de los archivos generados con easy-rsa.

$ sudo nano /etc/openvpn/server.conf

/etc/openvpn/server.conf

[…]
ca easy-rsa/keys/server.crt
cert easy-rsa/keys/server.crt
key easy-rsa/keys/server.key # Este archivo debería permanecer secreto
[…]

Ya estamos en condiciones de iniciar el servidor.

$ sudo service openvpn start

 

Configuración de los clientes

El primer paso será construir la clave de identificación del cliente

$ su -
Contraseña:

# cd /etc/openvpn/easy-rsa

# ./build-key cliente1
Donde cliente1, cliente2, clienteN serán el nombre que le daremos a cada cliente que deseemos conectar

Ahora trabajaremos en el archivo de configuración. Primero, copiamos el archivo de ejemplo en la documentación de openvpn y lo abrimos para su edición:

$ sudo cp /usr/share/doc/openvpn/examples/sample-config-files/client.conf /etc/openvpn/easy-rsa/keys/cliente1.ovpn

$ sudo nano /etc/openvpn/easy-rsa/keys/cliente1.ovpn

/etc/openvpn/easy-rsa/keys/cliente1.ovpn

[…]
# Tipo de túnel
;dev tun
dev tap
[…]
# Protocolo
;proto udp
proto tcp
[…]
# Dirección y puerto del servidor
remote ip_del_servidor 1194
remote miservidor.com 1194
remote miservidor2.org 1194
[…]
# Parámetros SSL/TLS
ca .vpn/ca.crt
cert .vpn/cliente1.crt
key .vpn/cliente1.key
[…]
# Privilegios de usuario
user nobody
group nobody
[…]

A partir de este momento dejamos el servidor y comenzamos a trabajar en el equipo cliente.

Creamos un directorio oculto en /home y mediante el uso de alguna herramienta de transferencia de archivos debemos copiar los archivos necesarios desde el servidor al cliente.

$ mkdir .vpn

$ scp usuario@ip_del_servidor:/etc/openvpn/easy-rsa/keys/{ca.crt,cliente1.crt,cliente1.key,cliente1.ovpn} .vpn/
Aquí utilizo scp (SSH) para transferir los archivos desde el servidor hacia el directorio oculto /home/.vpn en el cliente.

El último paso será iniciar el cliente. Si este cliente corre un sistema GNU/Linux, ejecutaremos en la consola:

$ sudo openvpn --config .vpn/cliente1.ovpn
Nota: en algunos sistemas es necesario ejecutar como superusuario

Seguridad adicional con TLS-AUTH

OpenVPN nos ofrece la posibilidad de mejorar la seguridad en la identificación a través de la verificación de las negociaciones mediante el uso de una firma de tipo HMAC. Para habilitar esta función, trabajaremos en la configuración tanto del servidor como del cliente.

En el servidor generamos la clave secreta y luego editamos el archivo de configuración:

$ sudo openvpn -genkey -secret ta-key

$ sudo nano /etc/openvpn/server.conf

/etc/openvpn/server.conf

[…]
tls-auth ta.key 0
[…]

Nota: en el servidor el valor es 0 (tráfico entrante)

En el cliente, copiamos la clave ta.key en el directorio de configuración de openvpn y editamos el archivo de configuración del cliente

$ sudo nano /etc/openvpn/cliente1.ovpn

/etc/openvpn/server.conf

[…]
tls-auth ta.key 1
[…]

Nota: en el servidor el valor es 1 (tráfico saliente)

OpenVPN en dispositivos móviles

Si sos de los que usan su teléfono para todo, inclusive trabajar, podrás utilizar el servicio VPN que acabamos de implementar para conectarte a tu red de área local. Para esto, instalaremos una aplicación que podemos encontrar en los repositorios de F-Droid: “OpenVPN for Android”.

Una vez instalada, copiamos al dispositivo los archivos necesarios (digamos: ca.crt, cliente_cyanogenmod.crt, cliente_cyanogenmod.key, cliente_cyanogenmod.ovpn), iniciamos la aplicación, seleccionamos los archivos y configuramos según los datos que correspondan a la conexión.

Palabras finales

Para finalizar el artículo es mi deber aclararles que para no extenderme demasiado decidí no entrar en detalle respecto de cómo asegurar el servidor contra los distintos ataques que pueda recibir, por lo que será tarea para ustedes ponerse a investigar y a trabajar en la seguridad de su servidor VPN.

Anuncios

Responder

Introduce tus datos o haz clic en un icono para iniciar sesión:

Logo de WordPress.com

Estás comentando usando tu cuenta de WordPress.com. Cerrar sesión / Cambiar )

Imagen de Twitter

Estás comentando usando tu cuenta de Twitter. Cerrar sesión / Cambiar )

Foto de Facebook

Estás comentando usando tu cuenta de Facebook. Cerrar sesión / Cambiar )

Google+ photo

Estás comentando usando tu cuenta de Google+. Cerrar sesión / Cambiar )

Conectando a %s