Czy można mieć wiele bram domyślnych dla połączeń wychodzących?

15

Chciałbym mieć wiele kart sieciowych (eth0 i wlan0) w tej samej podsieci i służyć jako kopia zapasowa aplikacji na hoście, jeśli jedna z kart sieciowych zawiedzie. Z tego powodu stworzyłem dodatkową tabelę routingu. Oto jak /etc/network/interfaceswygląda:

iface eth0 inet static
address 192.168.178.2
netmask 255.255.255.0
dns-nameserver 8.8.8.8 8.8.4.4
    post-up ip route add 192.168.178.0/24 dev eth0 src 192.168.178.2
    post-up ip route add default via 192.168.178.1 dev eth0
    post-up ip rule add from 192.168.178.2/32
    post-up ip rule add to 192.168.178.2/32

iface wlan0 inet static
wpa-conf /etc/wpa_supplicant.conf
wireless-essid xyz
address 192.168.178.3
netmask 255.255.255.0
dns-nameserver 8.8.8.8 8.8.4.4
    post-up ip route add 192.168.178.0/24 dev wlan0 src 192.168.178.3 table rt2
    post-up ip route add default via 192.168.178.1 dev wlan0 table rt2
    post-up ip rule add from 192.168.178.3/32 table rt2
    post-up ip rule add to 192.168.178.3/32 table rt2

Działa to w przypadku łączenia się z hostem: nadal mogę do niego SSH, jeśli jeden z interfejsów zawiedzie. Jednak aplikacje na hoście nie mogą zainicjować połączenia ze światem zewnętrznym, jeśli nie eth0działa. To jest mój problem.

Przeszukałem ten temat i znalazłem następujące interesujące informacje:

Gdy program inicjuje połączenie wychodzące, normalne jest używanie wieloznacznego adresu źródłowego (0.0.0.0), co oznacza brak preferencji co do tego, który interfejs jest używany, pod warunkiem że odpowiedni adres docelowy jest osiągalny. Nie jest on zastępowany określonym adresem źródłowym, dopóki nie zostanie podjęta decyzja o routingu. Ruch związany z takimi połączeniami nie będzie zatem zgodny z żadną z powyższych reguł zasad i nie będzie kierowany do żadnej z nowo dodanych tabel routingu. Zakładając normalną konfigurację, zamiast tego przejdzie do głównej tabeli routingu. http://www.microhowto.info/howto/ensure_symmetric_routing_on_a_server_with_multiple_default_gateways.html

Chcę, aby główna tabela tras miała więcej niż jedną bramę domyślną (jedną włączoną eth0i jedną włączoną wlan0) oraz przejść do domyślnej bramy eth0domyślnie i przez wlan0if, jeśli nie eth0działa.

Czy to jest możliwe? Co muszę zrobić, aby osiągnąć taką funkcjonalność?

rosix
źródło
Bardzo krótko: kilka domyślnych tras wybiera losowo jeden interfejs, co prowadzi do problemów, ponieważ przypisany adres IP jest inny. To, czego chcesz, to połączenie wielostronne lub pakietowe , co jest trudne do zrobienia, patrz np. Tutaj
reż.
1
Możesz użyć dynamicznego przełączania awaryjnego z łączeniem . Nie ma potrzeby majstrowania przy domyślnych trasach.
Ingo

Odpowiedzi:

17

Sam to rozwiązałem. Wydaje się, że jest bardzo mało informacji na temat pracy w sieci z Linuksem, więc postanowiłem szczegółowo udokumentować i wyjaśnić moje rozwiązanie. Oto moja końcowa konfiguracja:

  • 3 karty sieciowe: eth0 (drut), wlan0 (wbudowane Wi-Fi, słabe), wlan1 (adapter WiFi USB, silniejszy sygnał niż wlan0)
  • Wszystkie w jednej podsieci, każda z własnym adresem IP.
  • eth0 powinien być domyślnie używany zarówno dla ruchu przychodzącego jak i wychodzącego.
  • Jeśli eth0 zawiedzie, należy użyć wlan1.
  • Jeśli wlan1 zawiedzie, należy użyć wlan0.

Pierwszy krok : utwórz nową tabelę tras dla każdego interfejsu w /etc/iproute2/rt_tables. Nazwijmy je rt1, rt2 i rt3

#
# reserved values
#
255 local
254 main
253 default
0 unspec
#
# local
#
#1  inr.ruhep
1 rt1
2 rt2
3 rt3

Drugi krok : konfiguracja sieci w /etc/network/interfaces. To jest główna część i postaram się wyjaśnić jak najwięcej:

auto eth0 wlan0
allow-hotplug wlan1

iface lo inet loopback

iface eth0 inet static
address 192.168.178.99
netmask 255.255.255.0
dns-nameserver 8.8.8.8 8.8.4.4
    post-up ip route add 192.168.178.0/24 dev eth0 src 192.168.178.99 table rt1
    post-up ip route add default via 192.168.178.1 dev eth0 table rt1
    post-up ip rule add from 192.168.178.99/32 table rt1
    post-up ip rule add to 192.168.178.99/32 table rt1
    post-up ip route add default via 192.168.178.1 metric 100 dev eth0
    post-down ip rule del from 0/0 to 0/0 table rt1
    post-down ip rule del from 0/0 to 0/0 table rt1

iface wlan0 inet static
wpa-conf /etc/wpa_supplicant.conf
wireless-essid xyz
address 192.168.178.97
netmask 255.255.255.0
dns-nameserver 8.8.8.8 8.8.4.4
    post-up ip route add 192.168.178.0/24 dev wlan0 src 192.168.178.97 table rt2
    post-up ip route add default via 192.168.178.1 dev wlan0 table rt2
    post-up ip rule add from 192.168.178.97/32 table rt2
    post-up ip rule add to 192.168.178.97/32 table rt2
    post-up ip route add default via 192.168.178.1 metric 102 dev wlan0
    post-down ip rule del from 0/0 to 0/0 table rt2
    post-down ip rule del from 0/0 to 0/0 table rt2

iface wlan1 inet static
wpa-conf /etc/wpa_supplicant.conf
wireless-essid xyz
address 192.168.178.98
netmask 255.255.255.0
dns-nameserver 8.8.8.8 8.8.4.4
    post-up ip route add 192.168.178.0/24 dev wlan1 src 192.168.178.98 table rt3
    post-up ip route add default via 192.168.178.1 dev wlan1 table rt3
    post-up ip rule add from 192.168.178.98/32 table rt3
    post-up ip rule add to 192.168.178.98/32 table rt3
    post-up ip route add default via 192.168.178.1 metric 101 dev wlan1
    post-down ip rule del from 0/0 to 0/0 table rt3
    post-down ip rule del from 0/0 to 0/0 table rt3

Po wpisaniu ip rule showpowinieneś zobaczyć następujące informacje:

0:  from all lookup local 
32756:  from all to 192.168.178.98 lookup rt3 
32757:  from 192.168.178.98 lookup rt3 
32758:  from all to 192.168.178.99 lookup rt1 
32759:  from 192.168.178.99 lookup rt1 
32762:  from all to 192.168.178.97 lookup rt2 
32763:  from 192.168.178.97 lookup rt2 
32766:  from all lookup main 
32767:  from all lookup default 

To mówi nam, że ruch przychodzący lub wychodzący z adresu IP „192.168.178.99” będzie korzystał z tablicy tras rt1. Jak na razie dobrze. Ale ruch generowany lokalnie (na przykład chcesz pingować lub ssh z komputera do innego miejsca) wymaga specjalnego traktowania (patrz duży cytat w pytaniu).

Pierwsze cztery linijki post-up /etc/network/interfacessą proste, a wyjaśnienia można znaleźć w Internecie, piąta i ostatnia linijka post-up to magia:

post-up ip r add default via 192.168.178.1 metric 100 dev eth0

Zwróć uwagę, że nie określono tabeli tras dla tej linii post-up. Jeśli nie określisz tabeli tras, informacje zostaną zapisane w maintabeli tras, w której widzieliśmy ip rule show. Ta linia post-up umieszcza domyślną trasę w „głównej” tabeli tras, która jest używana dla ruchu generowanego lokalnie, który nie jest odpowiedzią na ruch przychodzący. (Na przykład MTA na twoim serwerze próbuje wysłać wiadomość e-mail).

Wszystkie trzy interfejsy umieszczają domyślną trasę w głównej tabeli tras, aczkolwiek z różnymi wskaźnikami. Rzućmy okiem na maintabelę tras z ip route show:

default via 192.168.178.1 dev eth0  metric 100 
default via 192.168.178.1 dev wlan1  metric 101 
default via 192.168.178.1 dev wlan0  metric 102 
192.168.178.0/24 dev wlan0  proto kernel  scope link  src 192.168.178.97 
192.168.178.0/24 dev eth0  proto kernel  scope link  src 192.168.178.99 
192.168.178.0/24 dev wlan1  proto kernel  scope link  src 192.168.178.98

Widzimy, że główna tabela tras ma trzy trasy domyślne, choć z różnymi metrykami. Najwyższy priorytet to eth0, następnie wlan1, a następnie wlan0, ponieważ niższe liczby wskaźników wskazują wyższy priorytet. Ponieważ eth0ma najniższą metrykę, jest to domyślna trasa, która będzie używana tak długo, jak eth0się da . Jeśli eth0spadnie, ruch wychodzący przełączy się na wlan1.

Dzięki tej konfiguracji możemy pisać ping 8.8.8.8w jednym terminalu, a ifdown eth0w drugim. pingpowinien nadal działać, ponieważ ponieważ ifdown eth0usunie domyślną trasę związaną z eth0, ruch wychodzący przełączy się na wlan1.

Linie post-down upewniają się, że powiązane tabele tras są usuwane z bazy danych strategii routingu ( ip rule show), gdy interfejs się psuje, aby wszystko było uporządkowane.

Pozostaje problem, że po wyciągnięciu wtyczki z eth0domyślnej trasy eth0nadal tam jest, a ruch wychodzący nie działa. Potrzebujemy czegoś do monitorowania naszych interfejsów i wykonywania, ifdown eth0jeśli występuje problem z interfejsem (np. Awaria karty sieciowej lub ktoś wyciąga wtyczkę).

Ostatni krok : wprowadź ifplugd. To demon, który obserwuje interfejsy i uruchamia się, ifup/ifdownjeśli wyciągniesz wtyczkę lub wystąpi problem z połączeniem Wi-Fi /etc/default/ifplugd:

INTERFACES="eth0 wlan0 wlan1"
HOTPLUG_INTERFACES=""
ARGS="-q -f -u0 -d10 -w -I"
SUSPEND_ACTION="stop"

Możesz teraz wyciągnąć wtyczkę eth0, ruch wychodzący przełączy się na, wlan1a jeśli ponownie włożysz wtyczkę, ruch wychodzący przełączy się z powrotem na eth0. Twój serwer pozostanie online tak długo, jak długo działa którykolwiek z trzech interfejsów. Aby połączyć się z serwerem, możesz użyć adresu IP eth0, a jeśli to się nie powiedzie, adres IP wlan1 lub wlan0.

rosix
źródło
Spróbuj nawiązać połączenie, które trwa dłużej (np. Scp dużego pliku), obserwuj używany interfejs sieciowy, wyłącz ten interfejs i zobacz, co się stanie.
bezpośrednio
scpSesja pęknie, ponieważ adres IP zmienia. W withsctptakim przypadku możesz spróbować użyć, aby utrzymać połączenie przy życiu lub użyć rsynczamiast, scpaby kontynuować przesyłanie od miejsca, w którym się zatrzymało.
rosix
Chodzi o to: jeśli się zepsuje, jaka jest przewaga skomplikowanej konfiguracji nad posiadaniem tylko jednej domyślnej trasy, powiedzmy na najszybszym aktualnie dostępnym interfejsie sieciowym? withsctpbędzie działać również tylko dla jednej domyślnej trasy.
reż
1
„jaka jest przewaga skomplikowanej konfiguracji nad posiadaniem tylko jednej domyślnej trasy, powiedzmy na najszybszym aktualnie dostępnym interfejsie sieciowym?” >> To właśnie robi moja konfiguracja. Domyślnie używana jest tylko najszybsza domyślna trasa (eth0). Nie ma za co.
rosix
11

Linux zapewnia lepsze rozwiązanie niż obejście skryptu: łączenie z aktywną kopią zapasową.

W ten sposób twój komputer będzie miał tylko jeden adres IP (i jeden adres mac) i automatycznie i przejrzyście przełącza interfejsy, jeśli jeden interfejs stanie się niedostępny. Brak zakłóceń jakiegokolwiek połączenia TCP (ani do wewnętrznej sieci LAN, ani do Internetu).

Sam używam tej konfiguracji do automatycznego przełączania awaryjnego z eth0 na wlan0 na moim laptopie Debian po odłączeniu laptopa od stacji dokującej.

Moje / etc / network / interfaces:

# The primary network interface
allow-hotplug eth0
iface eth0 inet manual
        bond-master bond0
        bond-primary eth0

# The secondary network interface
allow-hotplug wlan0
iface wlan0 inet manual
        pre-up sleep 5
        wpa-conf /etc/wpa_supplicant.conf
        bond-master bond0
        bond-primary eth0

# The bonding interface
allow-hotplug bond0
iface bond0 inet dhcp
        bond-slaves eth0 wlan0
        bond-primary eth0
        bond-mode active-backup
        bond-miimon 10
        bond_downdelay 10
        bond_updelay 4000

Możesz łatwo rozszerzyć tę konfigurację o wiele urządzeń WLAN. Ustawienie primary_reselectopcji better(automatycznie wybierz najszybszy link) powinno tu pomóc.

Aby uzyskać więcej informacji, zobacz https://wiki.linuxfoundation.org/networking/bonding i https://wiki.debian.org/Bonding

I (oczywiście) dokumentację jądra Linux na https://www.kernel.org/doc/Documentation/networking/bonding.txt

Thilo
źródło