LINUX.ORG.RU
ФорумAdmin

Плавающий адрес в iproute2

 , , ,


0

1

Добрый день.

Бьюсь над вопросом уже довольно долго, но решение никак не могу найти.

Задача: Настроить 2 плавающих адреса (внешний и внутренний) между двумя серверами ubuntu. Чтобы если один сервер упадёт, адреса переехали на другой сервер.

Данные: 10.10.255.171 - внутренний статический адрес сервера 10.10.255.170 - плавающий внутренний адрес 212.79.91.71 - плавающий внешний адрес

Дошел до запуска всего что нужно через iproute2 + netplan + keepalived

Netplan:

network:
    version: 2
    ethernets:
        ens160:
            addresses:
            - 10.10.255.171/25
            gateway4: 10.10.255.129

keepalived:

vrrp_instance internal {
    state MASTER
    interface ens160
    virtual_router_id 10
    priority 100
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass +hinFang75
    }
    virtual_ipaddress {
        10.10.255.170/25
    }
}

vrrp_instance external {
    state BACKUP
    interface ens160
    virtual_router_id 20
    priority 50
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass +hinFang75
    }
    virtual_ipaddress {
        212.79.91.71/28 gw 212.79.91.65 dev ens192
    }
}

При запуске системы поднимается keepalived и мне доступны оба внутренних адреса.

Теперь добавляю записи iproute2

iproute2:

Создаем таблицы
 echo '100 local' >> /etc/iproute2/rt_tables 
 echo '101 inet' >> /etc/iproute2/rt_tables

Добавляем дефолтный шлюз 
 ip route add default via 10.10.255.129 table 100
 ip route add default via 212.79.91.65 table 101

Определяем правила:
 ip rule add from 10.10.255.170 table 100
 ip rule add from 212.79.91.71  table 101

На этом этапе начинаю получать ответы по внешнему адресу, но только до перезапуска keepalived или интерфейса ens192. После перезапуска адрес появляется на интерфейсе, но больше не пингуется.

Я пробовал добавить метки на интерфейсы, но ничего не изменилось

Привязка ответа по тому же интерфейсу, по которому был получен пакет. 
 iptables -t mangle -A INPUT -i ens160 -j CONNMARK --set-mark 0x1 
 iptables -t mangle -A INPUT -i ens192 -j CONNMARK --set-mark 0x2
 iptables -t mangle -A OUTPUT -j CONNMARK --restore-mark 
 iptables -t mangle -A OUTPUT -m mark ! --mark 0x0 -j ACCEPT
 iptables -t mangle -A OUTPUT -d 10.10.255.170/32 -j MARK --set-mark 0x1
iptables -t mangle -A OUTPUT -d 212.79.91.71/32 -j MARK --set-mark 0x2


Теперь добавим правила роутинга так, чтобы с помощью файрвола выставив нужные значения fwmark мы могли выбрать нужную таблицу роутинга:

 ip rule add priority 101 fwmark 0x1/0x1 lookup  100
 ip rule add priority 102 fwmark 0x2/0x2 lookup  101

Я так понимаю проблема в том, что при перезапуске что-то срабатывает неправильно и пакеты для внешнего адреса пытаются уйти не через свой шлюз.

Гуру сети, подскажите пожалуйста, в каком направлении искать решение?

Ответ на: комментарий от KOTOXJle6

Это оно и есть.

Нет, keepalived не vrrpd. Это разные приложения, которые умеют vrrp. Просто у нас vrrpd используется, а настраивается очень просто.

Одна сторона:
/usr/sbin/vrrpd_wrapper -i eth0 -v 1 -p 100 10.1.1.20 -n

Другая сторона:
/usr/sbin/vrrpd_wrapper -i eth3 -v 1 -p 200 10.1.1.20 -n

AS ★★★★★
()
Ответ на: комментарий от AS

Такое не пробовал. Мне сейчас кажется что проблема не в vrrp и при использовании vrrpd будет то же самое.

Немного поковырялся. Если после перезапуска keepalived или интерфейса написать

ip route add default via 212.79.91.65 table 101

Адрес снова становится доступен. Но не знаю правильно ли так делать и если да, то должен выглядеть скрипт, который будет это делать автоматически?

KOTOXJle6
() автор топика
Ответ на: комментарий от AS

Возможно я просто не очень понятно объяснил. Схема реально сложная. Мне нужно чтобы одновременно были доступны 3 адреса: 1) внутренний адрес машины 2) внутренний общий адрес, который переезжает при падении сервера 3) внешний общий адрес, который переезжает при падении сервера

У внутренних адресов одинаковые шлюзы, а у внешнего адреса свой шлюз. Если шлюз не указывать отдельно, то адрес не работает. Дополнительные маршруты я тоже не прописываю, а ip route add default via 212.79.91.65 table 101 только указывает на таблицу, в которой прописан шлюз.

KOTOXJle6
() автор топика
Ответ на: комментарий от KOTOXJle6

1 - на каждом сервере всегда свой, тут понятно.
2 - если этот общий адрес всё из той же сети, где и два своих из первого пункта, то это всё просто, только ему и перескакивать, шлюз тут не меняется, если вся внутренняя сеть в одной сети.

Остаётся пункт 3. Ну вот тут смотреть. Во-первых, почему ты в OUTPUT -d используешь, а не -s? Тебе же по src ip надо решение принять, по какой таблице роутить. А во вторых, по идее, тут всё плохо: https://upload.wikimedia.org/wikipedia/commons/3/37/Netfilter-packet-flow.svg. OUTPUT применяется после routing decision.

AS ★★★★★
()
Последнее исправление: AS (всего исправлений: 1)
Ответ на: комментарий от AS

Добавил в keepalived после блока virtual_ipaddress вот это

 virtual_routes {
        0.0.0.0/0 gw 212.79.91.65 table 101
    }

Заработало как надо. Настроил второй сервер и немного погонял адреса между ними через service keepalived stop. Все переезжает без проблем. Единственное что немного напрягает - это потеря одного пакета примерно через каждые 20 пакетов, иногда чаще, иногда реже. Но это наверно уже к топику отношения не имеет.

Большое спасибо за помощь!

KOTOXJle6
() автор топика
Ответ на: комментарий от KOTOXJle6

К сожалению вскрылись новые проблемы. Не идет пинг с 212.79.91.71 никуда, дальше шлюза. Вероятно опять что-то не так со шлюзом, но странно что и изнутри сети и извне сам адрес пингуется.

KOTOXJle6
() автор топика
Ответ на: комментарий от KOTOXJle6

И все же не все работает как надо. Я писал выше что теряются пакеты, сегодня посмотрел через tcpdump, оказалось что при пинге из любого места до 212.79.91.71 ICMP echo request приходит на ens192, а reply уходит с ens160.

Если есть какие-нибудь идеи, прошу поделиться.

KOTOXJle6
() автор топика
Ответ на: комментарий от KOTOXJle6

Вероятно это был просто глюк, возможно вызванный CONNMARK. При новых тестах проблему получилось воспроизвести только один раз при жестком отключении сетевой карты от виртуальной машины в vsphere. При перемещении адреса из-за отключения keepalived всё работает стабильно.

KOTOXJle6
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.