Перенаправить DNS-трафик через туннельный интерфейс, весь остальной трафик использовать таблицу маршрутизации ядра

Перенаправить DNS-трафик через туннельный интерфейс, весь остальной трафик использовать таблицу маршрутизации ядра

Как перенаправить только DNS-трафик на использование туннельного интерфейса, когда он активен?

Любой другой тип трафика должен использовать таблицу маршрутизации ядра. Всякий раз, когда интерфейс туннеля не активен, трафик DNS должен использовать таблицу маршрутизации ядра. Возможно ли это с iptables?

Примечание: Я использую Strongswan 5.9.1, поэтому если есть способ настроить эту функциональность из Strongswan, я бы хотел это сделать. Однако я использую систему как политику на основе маршрутов. Кроме того, я в настоящее время маркирую пакеты с помощью strongswan, не уверен, связано ли это.

Интерфейсы:

# ip -br a
lo               UNKNOWN        127.0.0.1/8 ::1/128
ens3             UP             192.168.0.15/24 fe80::e74:fcff:fe28:cb00/64
ens4             UP             2.2.1.2/30 fe80::e74:fcff:fe28:cb01/64
virbr0           DOWN           192.168.122.1/24
virbr0-nic       DOWN
ip_vti0@NONE     DOWN
vti01@NONE       UNKNOWN        172.21.0.3/32 fe80::200:5efe:202:102/64

Маршруты:

# route -n
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         192.168.0.1     0.0.0.0         UG    0      0        0 ens3
2.2.0.1         0.0.0.0         255.255.255.255 UH    101    0        0 ens4
2.2.1.0         0.0.0.0         255.255.255.252 U     101    0        0 ens4
3.3.0.0         2.2.0.1         255.255.255.252 UG    101    0        0 ens4
3.3.1.0         2.2.1.1         255.255.255.252 UG    101    0        0 ens4
10.212.134.0    192.168.0.1     255.255.255.0   UG    100    0        0 ens3
172.21.0.0      0.0.0.0         255.255.255.248 U     0      0        0 vti01
192.168.0.0     0.0.0.0         255.255.255.0   U     100    0        0 ens3
192.168.122.0   0.0.0.0         255.255.255.0   U     0      0        0 virbr0

Я попробовал использовать следующее правило:

# iptables -t mangle -A OUTPUT -p udp --dport 53 --out-interface vti01

Я вижу правило, но когда я его просматриваю, то вижу, что при выполнении запроса dig на том же хосте пакеты не поступают в правило.

# watch -n1 iptables -t mangle -nvL

Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination
    0     0            udp  --  *      vti01   0.0.0.0/0            0.0.0.0/0            udp dpt:53

Что я упускаю?

решение1

Спасибо @AB Я использовал следующие команды (обратите внимание, что я сделал идентификатор таблицы таким же, как номер протокола DNS [53]):

ip route add table 53 0.0.0.0/0 dev vti01
ip rule add iif lo ipproto udp dport 53 lookup 53
sysctl -w net.ipv4.conf.vti01.rp_filter=2

Для проверки статуса я выполнил следующее:

ip route list table 53
ip rule list | grep 53

Мне удалось реализовать это в моем пользовательском скрипте _updown, поэтому Strongswan создавал и удалял эти записи каждый раз, когда туннель поднимается или опускается, и это работает.

#!/bin/bash

set -o nounset
set -o errexit

VTI_IF="vti01"
PORT="53"
TABLE="53"

case "${PLUTO_VERB}" in
    up-client)
        ip tunnel add $VTI_IF local 2.2.1.2 remote 3.3.0.2 mode vti key 41
        ip link set $VTI_IF up
        ip addr add  172.21.0.3 dev $VTI_IF
        ip route add 172.21.0.0/29 dev $VTI_IF
        ip route add table $TABLE 0.0.0.0/0 dev $VTI_IF
        ip rule add iif lo ipproto udp dport $PORT lookup $TABLE
        sysctl -w "net.ipv4.conf.$VTI_IF.rp_filter=2"
        sysctl -w "net.ipv4.conf.$VTI_IF.disable_policy=1"
        sysctl -w "net.ipv4.conf.$VTI_IF.rp_filter=0"
        sysctl -w "net.ipv4.conf.$VTI_IF.forwarding=1"
        ;;
    down-client)
        ip rule del iif lo ipproto udp dport $PORT lookup $TABLE
        ip route del table $TABLE 0.0.0.0/0 dev $VTI_IF
        ip tunnel del $VTI_IF
        ;;
esac

Затем я вызываю свой скрипт в файле swanctl.conf, вот как выглядит соединение. Раздел под дочерним элементом "updown=" — это способ вызова скрипта.

connections {
    remote-sa {
        version = 2 
        local {
            id = 2.2.1.2
        }   
        local_addrs = 2.2.1.2
        remote_addrs = 3.3.0.2
        proposals = aes256-sha256-ecp384
        local {
            auth = psk 
        }   
        remote {
            auth = psk 
        }   
        children {
            remote-sa-child {
                local_ts = 172.21.0.0/29
                remote_ts = 0.0.0.0/0
                mark_in = 41
                mark_out = 41
                esp_proposals = aes256-sha256-ecp384
                updown = /opt/_updown_vti01 iptables
                start_action = start
                close_action = start
            }
        }
    }   
}

Связанный контент