// DevOps

Enrutamos el tráfico de la subred local a través de un servidor remoto (IPIP + enrutamiento por políticas)

Publicado el 22.09.2026

La guía muestra cómo configurar dos servidores Linux para que todo el tráfico de Internet de una subred local concreta (por ejemplo, 10.100.10.0/24) no salga por su puerta de enlace habitual, sino a través de un túnel IPIP hacia un servidor remoto que lo publica en Internet.

El esquema es útil cuando los servicios de una subred deben salir a Internet con la dirección IP de otro servidor: para NAT centralizado, trabajar con socios que tengan listas blancas de direcciones o un único punto de salida para varias ubicaciones. El resto del tráfico del propio gateway sigue su ruta habitual.

IPIP no cifra el tráfico. Si el túnel atraviesa Internet y los datos deben protegerse, use WireGuard o IPsec — sobre opciones de conexión entre ubicaciones vea el artículo «Respaldo de canales de comunicación: entre oficinas».


Datos iniciales (direcciones de ejemplo)

RolNombreIP externa (WAN)Interfaz WANDirección en el túnelNota
Servidor APuerta de enlace local198.51.100.10eth010.254.0.1/30Puerta de enlace de la subred 10.100.10.0/24
Servidor BNodo remoto de salida203.0.113.20eth010.254.0.2/30Envía el tráfico a Internet
  • Subred a enrutar: 10.100.10.0/24
  • Nombre del túnel: ipip0
  • Red del túnel: 10.254.0.0/30

Paso 1: Configuración del servidor B (nodo de salida)

Objetivo: aceptar el túnel IPIP desde el servidor A y publicar el tráfico de la subred 10.100.10.0/24 en Internet mediante NAT con la dirección 203.0.113.20.

1.1. Habilitar el reenvío de paquetes

bash
sysctl -w net.ipv4.ip_forward=1
echo "net.ipv4.ip_forward = 1" > /etc/sysctl.d/90-ipip-forward.conf

1.2. Túnel, ruta de retorno, firewall y NAT

bash
#!/bin/sh
set -e

TUN_NAME="ipip0"
REMOTE_IP="198.51.100.10"
LOCAL_IP="203.0.113.20"
TUN_NET="10.254.0.2/30"
TUN_PEER="10.254.0.1"
WAN_IFACE="eth0"
CLIENT_NET="10.100.10.0/24"

echo "[*] Creando el túnel $TUN_NAME"
ip tunnel del "$TUN_NAME" 2>/dev/null || true
ip tunnel add "$TUN_NAME" mode ipip remote "$REMOTE_IP" local "$LOCAL_IP" ttl 64
ip addr add "$TUN_NET" dev "$TUN_NAME"
ip link set "$TUN_NAME" up mtu 1480

echo "[*] Añadiendo ruta de retorno a la subred de clientes vía el túnel"
ip route replace "$CLIENT_NET" via "$TUN_PEER" dev "$TUN_NAME"

echo "[*] Configurando iptables"
iptables -I INPUT -p 4 -s "$REMOTE_IP" -j ACCEPT
iptables -A FORWARD -i "$TUN_NAME" -s "$CLIENT_NET" -o "$WAN_IFACE" -j ACCEPT
iptables -A FORWARD -i "$WAN_IFACE" -d "$CLIENT_NET" -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT

iptables -t nat -A POSTROUTING -s "$CLIENT_NET" -o "$WAN_IFACE" -j SNAT --to-source "$LOCAL_IP"

iptables -t mangle -A FORWARD -o "$WAN_IFACE" -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu

echo "[OK] Servidor B listo."

La ruta de retorno es obligatoria: tras la traducción inversa las respuestas van dirigidas a máquinas de la subred 10.100.10.0/24, y sin esta ruta el servidor B las enviará a Internet en lugar de al túnel.

IPIP añade 20 bytes de cabecera a cada paquete, por eso el MTU del túnel es 1480. La regla TCPMSS --clamp-mss-to-pmtu reduce el tamaño de los segmentos TCP para ajustarlos a este MTU, evitando que las conexiones queden colgadas por problemas con PMTU Discovery.


Paso 2: Configuración del servidor A (puerta de enlace local)

Objetivo: dirigir el tráfico de la subred 10.100.10.0/24 que vaya a Internet hacia el túnel al servidor B.

2.1. Reenvío de paquetes y rp_filter

bash
sysctl -w net.ipv4.ip_forward=1
sysctl -w net.ipv4.conf.all.rp_filter=2
sysctl -w net.ipv4.conf.default.rp_filter=2

cat <<EOF > /etc/sysctl.d/90-ipip-gw.conf
net.ipv4.ip_forward = 1
net.ipv4.conf.all.rp_filter = 2
net.ipv4.conf.default.rp_filter = 2
EOF

El modo rp_filter=2 (loose) es necesario porque la ruta es asimétrica: las respuestas desde Internet llegan por el túnel y no por la interfaz a la que apunta la ruta por defecto. El kernel aplica el máximo entre los valores all y los de interfaz — por qué y cómo comprobarlo está descrito en el artículo «¿Qué es rp_filter?».


2.2. Creamos el túnel IPIP

bash
#!/bin/sh
set -e

TUN_NAME="ipip0"
REMOTE_IP="203.0.113.20"
LOCAL_IP="198.51.100.10"
TUN_NET="10.254.0.1/30"
TUN_PEER="10.254.0.2"

echo "[*] Levantando el túnel $TUN_NAME"
ip tunnel del "$TUN_NAME" 2>/dev/null || true
ip tunnel add "$TUN_NAME" mode ipip remote "$REMOTE_IP" local "$LOCAL_IP" ttl 64
ip addr add "$TUN_NET" dev "$TUN_NAME"
ip link set "$TUN_NAME" up mtu 1480

echo "[OK] Túnel levantado."

2.3. Enrutamiento por políticas

Añadimos la tabla de enrutamiento

bash
grep -q "100[[:space:]]tunnel_route" /etc/iproute2/rt_tables || echo "100 tunnel_route" >> /etc/iproute2/rt_tables

Si el archivo /etc/iproute2/rt_tables no existe en el sistema, créelo manualmente o use el número de tabla 100 en los comandos en lugar del nombre.

Añadimos la ruta por defecto en esta tabla

bash
ip route add default via 10.254.0.2 dev ipip0 table tunnel_route

Creamos la regla

bash
ip rule add from 10.100.10.0/24 table tunnel_route pref 1000
ip route flush cache

La regla envía al túnel todo el tráfico de la subred, incluidas las comunicaciones con otras redes locales. Si la subred debe comunicarse directamente con redes vecinas, añada antes otra regla con un número menor, por ejemplo:

bash
ip rule add from 10.100.10.0/24 to 10.0.0.0/8 table main pref 900

2.4. Firewall

bash
CLIENT_NET="10.100.10.0/24"
TUN_NAME="ipip0"

iptables -A FORWARD -s "$CLIENT_NET" -o "$TUN_NAME" -j ACCEPT
iptables -A FORWARD -i "$TUN_NAME" -d "$CLIENT_NET" -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT
iptables -t mangle -A FORWARD -o "$TUN_NAME" -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu

echo "[OK] Firewall y enrutamiento por políticas configurados."

Paso 3: Verificación

Ruta para el tráfico del propio servidor A

bash
ip route get 8.8.8.8

Se espera la ruta normal:

8.8.8.8 via <tu_puerta_de_enlace> dev eth0 src 198.51.100.10 ...

Ruta para un paquete desde la subred

Para verificar el reenvío, especifique la interfaz por la que llegó el paquete desde la red local (iif): sin ello el kernel comprueba la ruta para un paquete generado en el propio servidor.

bash
ip route get 8.8.8.8 from 10.100.10.50 iif eth1

Aquí eth1 es la interfaz del servidor A hacia la subred 10.100.10.0/24. Se espera una ruta a través del túnel:

8.8.8.8 from 10.100.10.50 via 10.254.0.2 dev ipip0 ...

Diagnóstico

1. Túnel

bash
ip addr show dev ipip0
ip -s tunnel show
ping -I ipip0 10.254.0.2

Si el ping no responde, verifique que los firewalls de ambos servidores y los del proveedor permitan el protocolo IPIP (protocolo IP 4).


2. Enrutamiento por políticas

bash
ip rule show
ip route show table tunnel_route

En la salida de ip rule show debe aparecer una línea:

1000: from 10.100.10.0/24 lookup tunnel_route

3. NAT en el servidor B

bash
iptables -t nat -L POSTROUTING -v -n

Con tráfico activo, los contadores de la regla SNAT deben aumentar.


4. Dirección externa para máquinas de la subred

En cualquier máquina de la subred 10.100.10.0/24:

bash
curl -4 ifconfig.me

Se espera 203.0.113.20.


5. MTU y MSS

Si las conexiones TCP se quedan colgadas:

bash
ip link show ipip0
ping -M do -s 1452 8.8.8.8

Un paquete con 1452 bytes de datos más 28 bytes de cabeceras ICMP e IP encaja justo en el MTU del túnel 1480. Compruebe que el túnel tenga mtu 1480 y que la regla --clamp-mss-to-pmtu esté aplicada.


6. tcpdump

bash
tcpdump -ni ipip0
tcpdump -ni eth0 host 8.8.8.8

7. Registro temporal

bash
iptables -I FORWARD 1 -j LOG --log-prefix "[FORWARD] "
tail -f /var/log/kern.log

Tras el diagnóstico elimine esta regla: escribe en el registro cada paquete reenviado.


8. Ruta inversa

Desde una máquina de la subred:

bash
traceroute 8.8.8.8

El primer salto debe ser el servidor A, el siguiente la dirección del servidor B en el túnel 10.254.0.2. Desde el servidor B:

bash
traceroute -s 10.254.0.2 10.100.10.10

Si la trazada desde el servidor B sale a Internet en lugar de por el túnel, compruebe la ruta de retorno del paso 1.2.


9. Guardar la configuración

Los comandos anteriores son volátiles hasta el reinicio. Las reglas de iptables se guardan así (en Debian y Ubuntu — paquete iptables-persistent):

bash
iptables-save > /etc/iptables/rules.v4

El túnel, las rutas y las reglas de enrutamiento por políticas deben recrearse tras el reinicio: lo más cómodo es empaquetar los scripts de los pasos 1.2, 2.2 y 2.3 en un servicio systemd. Guardar la salida de ip rule show en un archivo por sí solo no restaura nada.


Recomendaciones adicionales

ElementoRecomendación
MTU1480 para el túnel y TCPMSS clamp en ambos servidores
FirewallEn sistemas nuevos es más cómodo usar nftables
Inicio automáticoLevantar el túnel y las rutas mediante systemd
Monitorizacióntcpdump -i ipip0 muestra el tráfico en el túnel
SeguridadPermita IPIP sólo desde la dirección del segundo servidor; para cifrado — WireGuard o IPsec

Una tarea similar en MikroTik — devolver la respuesta por la misma puerta por la que llegó la petición — está tratada en el artículo «MikroTik: devolver el tráfico por la misma puerta».


Resumen

Todo el tráfico de Internet de la subred 10.100.10.0/24 sale a Internet con la dirección del servidor B (203.0.113.20), mientras que el servidor A sigue usando su ruta habitual. Para que el esquema funcione hacen falta tres cosas: un túnel con el MTU correcto, una regla de enrutamiento por políticas en el servidor A y una ruta de retorno a la subred en el servidor B.

// Contact

¿Necesitas ayuda?

Escríbeme y te ayudaré a resolver el problema

Respondo en un día laborable (03:00-13:00 GMT)

Или оставьте заявку здесь:

Confirme que no es un bot.

Escribir y recibir una respuesta rápida