Pull to refresh

По просьбам трудящихся: Dual ISP на маршрутизаторах cisco без BGP

Reading time 4 min
Views 60K
Типичная задача, которая тем не менее, продолжает вызывать массу вопросов.

Попробую вкратце описать суть технологии и подводные камни.

Итак, пусть у нас есть один пограничный маршрутизатор cisco с одним внутренним портом (g0/0) и двумя внешними (f0/0, f0/1). Есть подключение к двум провайдерам, каждый из которых выдал свой пул адресов Pool(ISP1) и Pool(ISP2) (это некоторые сети, принадлежащие конкретному провайдеру). Пусть для простоты адреса интерфейсов f0/0 и f0/1 из этих же пулов. И адреса шлюзов из этих же пулов (Gate(ISP1) и Gate(ISP2) соответственно).
Так как у нас нет возможности поднять BGP, значит мы должны на каждого из провайдеров прописать маршрут по умолчанию. И вот тут возникает первый вопрос: какую задачу мы хотим решить? Резервирование или одновременная работа с двумя провайдерами?


Резервирование.

В этой топологии одновременно работает только один провайдер. То есть мы должны организовать проверку провайдера ISP1 и в случае если он живой – ходить через него, а если «мертв», то переключаться на запасного провайдера ISP2. Здесь есть подводный камень: NAT. Мы можем написать несколько правил трансляции, но надо как то указать, что при выходе через ISP1 мы используем Pool(ISP1), а при выходе через ISP2 – Pool(ISP2), иначе маршрутизатор всегда будет использовать трансляцию, которая первой написана в конфигурации. Понятно, что если идти через ISP2, а адреса источника будут из Pool(ISP1), то в лучшем случае мы получим несимметричную маршрутизацию, в худшем пакеты вообще никуда не дойдут, например потому, что провайдеры выполняют предписание использовать фильтрацию по RFC2827, что означает не принимать пакеты с адресами источника не из своей сети.
Итак, у нас 2 подзадачи: проверка провайдера (маршрута) на «живость» и трансляция адресов с учётом выходного интерфейса.

Проверка на «живость».

Маршрутизаторы cisco обладают замечательной технологией, называемой SLA. При помощи неё можно не только проверять пингом некий адрес, но также проверять живость определенных сервисов (ftp-connect, tcp-connect) или параметра канала связи (icmp-jitter, udp-jitter). Здесь рассмотрим самый простой и распространенный способ – пинг определенного хоста. Для простоты будем пинговать адрес шлюза провайдера Gate(ISPX). Если надо пинговать другой адрес, то необходимо явно прописать маршрут до этого адреса через конкретного провайдера, которого мы проверяем.

! Задаем параметры «пинговалики»
ip sla {#}
  icmp-echo {ip} [source-interface {int}]
!
! Запускаем пинговалку
ip sla schedule {#} start now life forever
!
! Настраиваем «переключатель» (track), от которого будет зависеть маршрут
track {#} ip sla {#} reachability
!
! Настраиваем маршрут по умолчанию с трекингом
ip route 0.0.0.0 0.0.0.0 {next-hop} track {#}


Примечание: в старых IOS команда привязки track к sla выгдялела так

track {#} rtr {sla#} reachability

Если хост пингуется, то track будет в состоянии UP и маршрут будет в таблице маршрутизации. А
если пинг пропадет, то через настроенный промежуток времени (по умолчанию 3*10 секунд) track
поменяет состояние на DOWN и маршрут будет удален до тех пор, пока track вновь не изменит
состояние.

Пример:
ip sla 1
  icmp-echo Gate(ISP1)
ip sla schedule 1 start now life forever
track 11 ip sla 1 reachability
ip route 0.0.0.0 0.0.0.0 Gate(ISP1) track 11

ISP2 можно не проверять, чтобы не создавать лишний служебный трафик в канал, т.к. он у нас запасной и может быть дорогим (спутниковый канал, к примеру, или коммутируемый канал, оплачиваемый по времени работы). Маршрут на второго провайдера мы напишем с большей административной дистанцией и тем самым заставим его работать только при пропадании основного.

Задание правил трансляции адресов с учетом исходящего интерфейса.


Тут на самом деле тоже 2 задачи: динамическая трансляция и статическая трансляция адресов. Первая нам нужна для выхода наружу, а вторая – для анонса сервисов. И в том и в другом случае нам понадобится конструкция, называющаяся route-map (создать надо будет по route-map на каждого провайдера)

! Создаем route-map
route-map ISPX permit {#}
  ! Указываем критерий попадания в этот абзац route-map  
  match interface {исходящий интерфейс}


Тут есть тонкость: при указании слова interface в подсказке пишется

  interface         Match first hop interface of route

Т.е. вообще говоря, не понятно, что это за параметр. Плюс в зависимости от того, что написано на самом интерфейсе, этот критерий может означать как входящий интерфейс, так и исходящий! А зависит это от того, что написано в команде ip nat на интерфейсе:

ip nat inside – критерий будет означать входящий интерфейс
ip nat outside – критерий будет означать исходящий интерфейс

Далее, нам понадобится пул адресов от каждого провайдера

  ip nat pool PoolX {start-ip(ISPX)}  {end-ip(ISPX)}

И можно уже писать правила NAT на каждого провайдера

  ip nat inside source route-map ISPX poolX overload

overload – ключевое слово, означающее использовать PAT (Port Address Translation, трансляцию с учётом порта источника)
Если к надо добавить статические трансляции, то делаем почти так же (пусть серверу мы зарезервировали адрес Srv(ISPX) от каждого провайдера, а локальный адрес у сервера – Srv(LAN).)

  ip nat inside source static Srv(ISPX) Srv(LAN) route-map ISPX


____________
UPD ВНИМАНИЕ: ВВЕРХУ ОПЕЧАТКА!
Должно быть
  ip nat inside source static Srv(LAN) Srv(ISPX) route-map ISPX 

____________

При этом конечно надо озаботиться, чтобы оба адреса (Srv(ISP1) и Srv(ISP2)) на ДНС серверах были прописаны и указывали на одно и то же имя.

Итого, у нас получилось:

! 
! интерфейсы
int g0/0
  ip address [LAN]
  ip nat inside
!
int f0/0
  ip address Address(ISP1)
  ip nat outside
!
int f0/1
  ip address Address(ISP2)
  ip nat outside
!
! Маршрутизация
ip sla 1
  icmp-echo Gate(ISP1)
ip sla schedule 1 start now life forever
track 11 ip sla 1 reachability
ip route 0.0.0.0 0.0.0.0 Gate(ISP1) track 11
ip route 0.0.0.0 0.0.0.0 Gate(ISP2) 50
!
! Пулы для NAT
ip nat pool POOL1 {start-ip(ISP1)}  {end-ip(ISP1)}
ip nat pool POOL2 {start-ip(ISP2)}  {end-ip(ISP2)}
!
! route-map для NATa
route-map ISP1 permit 10
  match interface f0/0
!
route-map ISP2 permit 10
  match interface f0/1
!
! Правила NATa
ip nat inside source route-map ISP1 POOL1 overload
ip nat inside source route-map ISP2 POOL2 overload
ip nat inside source static Srv(LAN) Srv(ISP1) route-map ISP1
ip nat inside source static Srv(LAN) Srv(ISP2) route-map ISP2


Одновременное использование двух провайдеров

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

Интересна ли эта тема? Какие мысли и проблемы есть?
Пишите: скомпилирую со своими мыслями и выложу, если захотите.
Tags:
Hubs:
+18
Comments 35
Comments Comments 35

Articles