Configurando br0, sin VPN

Configurando br0, sin VPN

Estoy intentando forzar que todo el tráfico de un invitado (Windows o Linux) pase por la VPN del host (Linux). Para asegurarme de que un invitado no tenga acceso a Internet fuera de la VPN, establezco la conexión en el sistema anfitrión, lo que crea una nueva interfaz tun0. El túnel VPN funciona bien en el host.

Configurando br0, sin VPN

Para obtener Internet sin VPN en el invitado, creo un dispositivo puente br0y enp7s0lo conecto. De esta manera, Internet funciona en el huésped.

ip link add name br0 type bridge
ip link set br0 up
ip link set enp7s0 master br0

En el host, vnet5se agregó un dispositivo y se unió a él br0. Pero al mismo tiempo, hacer ping desde el host a un control remoto ya no funciona.

## On the Host
sudo ip a
# ...
# 14: vnet5: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master br0 state UNKNOWN group default qlen 1000
# link/ether ab:ab:ab:ab:ab:ab brd ff:ff:ff:ff:ff:ff
# inet6 fe80::fc54:ff:fe92:5aa9/64 scope link
# valid_lft forever preferred_lft forever
ping www.google.com
# ping: www.google.com: Temporary failure in name resolution
ping 8.8.8.8
# From 192.168.1.100 icmp_seq=1 Destination Host Unreachable

Luego inicio la VM virt-managery verifico la conexión. El huésped dispone de internet:

## On the Guest
ip a
# 1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
# ...
# 2: enp1s0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
#     link/ether 52:54:00:92:5a:a9 brd ff:ff:ff:ff:ff:ff
#     inet 192.168.1.221/24 brd 192.168.1.255 scope global dynamic noprefixroute enp1s0
#        valid_lft 67432sec preferred_lft 67432sec
ping www.google.ch
# PING www.google.ch (172.217.168.35) 56(84) bytes of data.
# 64 bytes from zrh04s14-in-f3.1e100.net (172.217.168.35): icmp_seq=1 ttl=117 time=2.47 ms

Supongo que en lugar de configurarlo, ip link set enp7s0 master br0también podría crear reglas de enrutamiento entre br0y enp7s0.

Con VPN y la tun0interfaz

Cuando establezco una conexión VPN, tun0se crea una interfaz que no se puede asignar a un puente. Por lo tanto, necesitaría crear reglas de enrutamiento de todos modos. Entonces supongo que la situación es similar al caso anterior. Primero, elimino enp7s0nuevamente de br0.

ip link set enp7s0 nomaster
sudo openvpn my_vpn_tcp.ovpn
# ...
# Initialization Sequence Completed
sudo ip a
# ...
# 3: enp7s0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
# link/ether ab:ab:ab:ab:ab:ab brd ff:ff:ff:ff:ff:ff permaddr ab:ab:ab:ab:ab:ab
# inet 192.168.1.100/24 brd 192.168.1.255 scope global dynamic noprefixroute enp7s0
# valid_lft 82702sec preferred_lft 82702sec
# ...
# 10: tun0: <POINTOPOINT,MULTICAST,NOARP,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UNKNOWN group default qlen 500
# link/none
# inet 10.7.7.5/24 scope global tun0
# valid_lft forever preferred_lft forever
# ...
# 12: br0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
# link/ether 72:eb:06:e5:1e:5a brd ff:ff:ff:ff:ff:ff
# inet6 fe80::70eb:6ff:fee5:1e5a/64 scope link
# valid_lft forever preferred_lft forever

Sin más, la conexión VPN se utiliza en el host, lo cual está bien.

ping www.google.com
# PING www.google.com (172.217.168.3) 56(84) bytes of data.
# 64 bytes from lala.net (172.217.168.3): icmp_seq=1 ttl=117 time=9.64 ms
# ...
ping www.google.com -I tun0
# PING www.google.com (172.217.168.3) from 10.7.7.5 tun0: 56(84) bytes of data.
# 64 bytes from lala.net (172.217.168.3): icmp_seq=2 ttl=117 time=10.0 ms
# ...
ping www.google.com -I enp7s0
# PING www.google.com (172.217.168.3) from 192.168.1.100 enp7s0: 56(84) bytes of data.
# 64 bytes from lala.net (172.217.168.3): icmp_seq=1 ttl=115 time=4.59 ms
# ...

Pero como ya dije, no puedo agregar tun0más br0. Y por eso el huésped tampoco tiene internet.

sudo ip link set tun0 master br0
# RTNETLINK answers: Invalid argument

Busqué soluciones pero no pude encontrar nada que funcionara o mi caso es ligeramente diferente, lo que requeriría más conocimientos sobre redes que no tengo. P.ejeste(que no hizo el trabajo) oeste(eso no se ajusta exactamente a mi caso).

Respuesta1

Hay dos preguntas en la misma pregunta y en realidad no dependen una de otra. Todavía responderé a ambos.

Además, la noprefixrouteopción de dirección sugiere que una parte de la configuración de la red se administra mediante alguna herramienta adicional (como NetworkManager) para agregar rutas. Esta respuesta no intentará abordar la integración en herramientas de red. Esto incluye lidiar con la configuración de DHCP, que podría anular los cambios más adelante si no se reconfigura correctamente. Muchas configuraciones desaparecen cuando la interfaz se desactiva o se elimina y deben realizarse nuevamente, por lo que es mejor hacerlo en varios ganchos de varias herramientas de red a cargo.

Configurando br0, sin VPN

Una interfaz configurada como puerto puente pierde su participación en el enrutamiento

Una vez configurado como puerto puente, las rutas asociadas con la interfaz se ignoran. Es posible que aún existan efectos secundarios dañinos al dejar la dirección en él. Los detalles se pueden encontrar en el blog.Aislamiento adecuado de un puente Linux:

  1. entregue el marco a la persona encargada del dispositivorecibir controlador, Si alguna,
  2. entregar el marco a un global o específico del dispositivomanejador de protocolo(por ejemplo, IPv4, ARP, IPv6).

Para una interfaz puenteada,El kernel ha configurado un controlador de recepción específico del dispositivo br_handle_frame(). Esta función no permitirá ningún procesamiento adicional en el contexto de la interfaz entrante, excepto para tramas STP y LLDP, o si la "generación" está habilitada. Por lo tanto,el Los controladores de protocolo nunca se ejecutan.en este caso.

La dirección IP configurada en una interfaz que se convirtió en un puerto puente debe trasladarse a la interfaz propia del puente especial ( br0: el puente en sí), que es la única capaz de participar en el enrutamiento (hay otras opciones, pero hagámoslo simple). Lo mismo ocurre con las rutas relevantes.

Supongamos que la puerta de enlace predeterminada de OP es 192.168.1.1/24. Reescribamos esto para el primer caso:

ip link add name br0 up type bridge
ip link set dev enp7s0 master br0

ip address flush dev enp7s0
# previous command will also have removed all associated routes as a side effect
ip address add 192.168.1.100/24 dev br0
# previous command added the LAN route too as a side effect (no noprefixroute here)
ip route add default via 192.168.1.1

Con esto, tanto el host como la VM pueden acceder a Internet.

Tenga en cuenta que, para la parte VM, vnet5también es un puerto puente y tampoco participa en el enrutamiento. El host simplemente cambia tramas entre la máquina virtual y el enrutador (192.168.1.1): no implica enrutamiento.

Con VPN y la tun0interfaz

OpenVPN se basa en el controlador TUN/TAP (proporcionado en Linux por el módulo del kerneltun). El conductor puede proporcionar:

  • ya sea una interfaz TAP de capa 2

    Se comporta como un dispositivo Ethernet y se puede configurar como un puerto puente Ethernet: lo vnet5crea el hipervisor VM.

  • o una interfaz TUN de capa 3

    No incluye información de trama (dirección MAC de Ethernet) ni maneja tramas, sino que trata solo con protocolos en la capa 3 o superior: IPv4 o IPv6. Por lo tanto, no se puede configurar como puerto puente Ethernet. Son OP tun0creados por OpenVPN en modo TUN.

OpenVPN también puede usar el modo TAP que podría conectarse en puente, pero esto requiere reconfigurar el control remoto.servidorlado también y todo el diseño de la red: el servidor remoto también sería parte de la LAN 192.168.1.0/24. OP no parece tener control sobre ello.

Entonces, consideremos lo que se puede hacer con la interfaz TUN del OP: esto se hará en la capa 3: enrutamiento, y no en la capa 2.

Reutilizar la configuración anterior solo para máquinas virtuales confiables

Si el host no incluye firewall avanzado, incluidas restricciones de firewall y/o alteraciones en la ruta del puente, no puede forzar a una VM a usarse como puerta de enlace: una VM con puente como antes puede simplemente ignorar el host y mantener 192.168.1.1 como puerta de enlace y que su tráfico no utilice la interfaz del host tun0al final.

Si se puede confiar en la VM y reconfigurarla, se puede seguir br0como se indicó anteriormente, aplicar cualquier configuración de OpenVPN basada en br0(reemplazando cualquier enp7s0referencia con br0) y hacer esto una vez que la VM se esté ejecutando (con la dirección 192.168.1.221) y la VPN esté activa:

  • en el anfitrión

    Usandoenrutamiento basado en políticas/fuentepara seleccionar un resultado de ruta diferente para esta fuente específica:

    ip rule add from 192.168.1.221 lookup 1000
    ip rule add iif tun0 lookup 1000
    ip route add 192.168.1.0/24 dev br0 table 1000
    ip route add default dev tun0 table 1000
    

    Establecer como enrutador:

    sysctl -w net.ipv4.ip_forward=1
    

Y en caso de que ninguna regla NAT similar ya resuelva este caso:

  iptables -t nat -A POSTROUTING -s 192.168.1.221 -o tun0 -j MASQUERADE
  • en VM (Linux), use el host como puerta de enlace en lugar del enrutador del host

    ip route flush to default
    ip route add default via 192.168.1.100
    

Recomendado para máquinas virtuales que no son de confianza: no configure la interfaz principal del host como puerto puente

Esto hace que sea más fácil controlar el tráfico de la VM tun0porque no tendrá vista de las partes de la red que no debe alterar.

  • cambiar la configuración de VM para usar su propia red IP

    Ejemplo: 192.168.100.0/24 y una IP estática 192.168.100.2/24 (en lugar del DHCP de la red del host), con una puerta de enlace predeterminada 192.168.100.1. En una máquina virtual Linux:

    ip address add 192.168.100.2/24 dev enp1s0
    ip route add default via 192.168.100.1
    
  • En el host, comience desde la configuración inicial (sin puentes enp7s0)

    Incluso se podría utilizar el puente cero a continuación (es decir, directamente ip address add 192.168.100.1/24 dev vnet5sin vnet5configurarlo como puerto puente), perolibvirtpodría hacer esto más difícil.

    Simplemente tenga un puente dedicado para máquinas virtuales (aquí usando la dirección 192.168.100.1/24, aunque generalmentelibvirtproporciona un puente predeterminado virbr0con 192.168.122.1/24):

    ip link add name br0 up type bridge
    ip address add 192.168.100.1/24 dev br0
    ip link set dev vnet5 master br0
    

    Y también usarenrutamiento de políticaspara cambiar el comportamiento del tráfico relacionado con las VM para las dos interfaces involucradas: br0y tun0. Como es habitual, implica algunas duplicaciones y modificaciones de rutas existentes en una tabla de enrutamiento alternativa. Aquí tun0se supone que solo se da servicio al host y sus máquinas virtuales. El objetivo final es: todo lo que viene del lado VM se enruta al lado tun, todo lo que viene del lado TUN se enruta al lado VM, sin tener en cuenta cualquier lado no necesario.

    ip rule add iif br0 lookup 2000
    ip rule add iif tun0 lookup 2000
    ip route add 192.168.100.0/24 dev br0 table 2000
    ip route add default dev tun0 table 2000 # layer 3 interfaces don't need a gateway
    

    Nota: los paquetes entrantes tun0destinados al host (es decir, no enrutados) ya son manejados por ellocaltabla de enrutamiento y no necesita ninguna ruta adicional en la tabla 2000.

    Establecer como enrutador:

    sysctl -w net.ipv4.ip_forward=1
    

    Luego complete con NAT ya que el servidor OpenVPN remoto no conoce 192.168.100.0/24:

    iptables -t nat -A POSTROUTING -s 192.168.100.0/24 -o tun0 -j MASQUERADE
    

Si la VM aún debería poder alcanzar la LAN 192.168.1.0/24:

  • actualice nuevamente la tabla 2000 para acomodar esto

    Duplicar la ruta LAN desde la tabla principal a la tabla 2000:

    ip route add 192.168.1.0/24 dev enp7s0 table 2000
    
  • y agregue nuevamente una regla MASQUERADE adecuada

    ... ya que VM ahora está en una LAN diferente que otros sistemas no conocen:

    iptables -t nat -A POSTROUTING -s 192.168.100.0/24 -o enp7s0 -j MASQUERADE
    

    (Se podrían realizar la factorización de algunas reglas de iptables).

información relacionada