IPv6 prefix delegation в реална ISP мрежа (част 1): /60 за всеки клиент и връзката с IPv4 билинга
Това е разказ за няколко дни, в които най-накрая пуснах IPv6 на първите бизнес клиенти, и за нещата, които ги няма в документацията. Писан е за колеги, които имат своя мрежа с граничен рутер, комутатори, радиолинкове и оптика, и които също го отлагат. Реалните адреси съм ги сменил: IPv6 префиксите са от документационния
2001:db8::/32, а IPv4 адресите — от198.51.100.0/24.
Задачата, която стоеше най-дълго в списъка
Всеки админ си има такава задача. Не е спешна, не е забравена и не се прави. Моята беше IPv6. Префиксът отдавна ни беше разпределен, BGP-то го анонсираше, граничният рутер го поддържаше, а клиентите продължаваха да живеят само на IPv4. Никой не се оплакваше и точно затова задачата винаги оставаше за следващия месец.
Истинската причина да я отлагам беше друга. Знаех, че IPv6 в ISP мрежа не се пуска с една отметка. Трябва да мине през радиата, оптиката и комутаторите, да се разбере с клиентските рутери и най-вече с билинга, който знае само за IPv4. Всяко от тези неща изглеждаше дребно, но заедно ставаха цяла седмица, която все не намирах.
През септември седнах и реших да не ставам, докато първите клиенти не получат префикси. Започнах с най-простия въпрос: какво точно да им дам.
Защо prefix delegation, а не SLAAC в клиентския VLAN
Първата ми мисъл беше най-мързеливата: по един /64 в споделения клиентски VLAN и край. После си представих как изглеждат бизнес клиентите ни отвътре. Почти всички имат собствен рутер, най-често MikroTik, а зад него няколко мрежи: офис, гости, камери, понякога отделни VLAN-и за различни отдели. С един /64 те нямат какво да разпределят навътре и ще ме потърсят още на първия ден.
Затова всеки получава цял /60 чрез DHCPv6 prefix delegation. Това са 16 отделни /64 мрежи, по една за всяка вътрешна мрежа на клиента. Границата на отговорност остава същата като при IPv4: до WAN порта на клиентския рутер е моя, зад него е негова.
Граничният рутер: строго от първия ден
Граничният рутер е MikroTik CCR2116 с RouterOS 7.24. Реших да започна строго, защото е по-лесно да отпуснеш правило, отколкото после да събираш раздадени адреси:
- от нашия
/48е заделен един/52за клиентски делегации — 256 броя/60; - по един DHCPv6 сървър на всеки клиентски VLAN, в който има бизнес клиенти;
- сървърите раздават само статични binding-и — непознато устройство не получава нищо.
/ipv6 pool
add name=pool1 prefix=2001:db8:100:1000::/52 prefix-length=60
/ipv6 dhcp-server
add name=vlan_65 interface=vlan65 address-pool=static-only prefix-pool=static-only \
lease-time=1d rapid-commit=yes
/ipv6 dhcp-server binding
add server=vlan_65 address=2001:db8:100:1010::/60 prefix-pool=pool1 life-time=1d \
duid=0x00030001021122334455 iaid=1 comment="198.51.100.57 Клиент А"
| Настройка | Защо |
|---|---|
prefix-pool=static-only |
Префикс получава само клиент, за който ръчно има binding. Същата логика като при IPv4 — никакви динамични адреси в клиентския VLAN. |
Маршрут към всеки /60 |
Рутерът сам слага динамичен маршрут към link-local адреса на клиентския рутер, щом binding-ът стане bound. |
BGP анонсира само /48 |
DHCP маршрутите не са нито connected, нито static, а out-филтрите пускат само агрегата. Двойна защита срещу изтичане на /60 към горните доставчици. |
Blackhole за /48 |
Незаетите /60 падат в него — трафик към тях не се връща към доставчика в цикъл. |
DNS: съобщението, което ме подведе
Първият префикс тръгна без драма и за около минута си помислих, че съм се страхувал напразно. После отворих /ipv6 nd на граничния рутер. На всеки запис стоеше бележка:
;;; automatic dns option advertising is not started, re-apply dns config
DHCPv6 сървърът пък нямаше нито един DNS option. Заключението изглеждаше очевидно: клиентите имат IPv6 адреси, но нямат IPv6 DNS. Отворих документацията на MikroTik. Там пише, че DHCP сървърът подава DNS от /ip dns, но само за IPv4, а за DHCPv6 не пише нищо. Потърсих съобщението от /ipv6 nd в документацията, в changelog-овете и във форума. Никъде го нямаше.
Вече бях започнал да мисля как да добавя DNS option на ръка, но реших първо да проверя от страната на клиента. На един клиентски рутер в /ip dns IPv6 адресът на нашия резолвер стоеше в dynamic-servers. Значи е получен, а не вписан. По-късно, в запис на DHCPv6 обмена, се видя и самият отговор на граничния рутер:
dhcp6 reply (... (rapid-commit) (DNS-server 2001:db8:100:2::6) (IA_PD IAID:2 ...))
Излезе, че DHCPv6 сървърът на RouterOS сам слага IPv6 сървърите от /ip dns в отговора. Съобщението в ND засяга само RDNSS в Router Advertisement. А RA-то клиентските рутери и без това го игнорират, защото са с forward=yes и accept-router-advertisements=yes-if-forwarding-disabled. Клиентският рутер после препредава DNS-а към своя LAN с RA. Всичко работеше, а аз едва не го „поправих“.
Липсата на нещо в документацията на MikroTik не значи, че функцията липсва. Проверявай на пакетно ниво, преди да „поправяш“ работеща конфигурация.
Въпросът, заради който отлагах: какво става, ако клиентът не плати
Това беше частта, която ме притесняваше от самото начало. Билингът управлява IPv4: налива статични DHCP lease-ове, а един скрипт на рутера на всеки час ги пуска или спира според списъка с платилите. За IPv6 билингът не знае нищо. Ако не направя нищо, клиент със спрян интернет ще продължи да си ходи по IPv6 и никой няма да забележи. Исках binding-ът да се спира заедно с IPv4 lease-а на същия клиент. За целта трябваше някак да ги свържа.
Защо не по MAC адрес
Първата идея изглеждаше толкова чиста, че бях сигурен в нея. DUID-ът тип LL съдържа MAC адрес, IPv4 lease-ът също. Остава само да ги сравня. Сравних ги за първите клиенти и не става:
| Какво видяхме | Защо е проблем |
|---|---|
| MAC-ът в DUID-а не е на WAN порта | По подразбиране DHCPv6 клиентът на RouterOS е с use-interface-duid=no и прави DUID от системен MAC (обикновено на ether1), а не от порта, през който иска префикс. |
| DUID сочи към друг договор | Един клиент имаше два акаунта на два порта на същия рутер. DUID-ът беше от първия порт, а IPv6 минаваше през втория. Връзка по MAC щеше да спре грешната услуга. |
| Клиенти без IPv4 lease | Някои са с ръчно зададен IPv4 адрес — няма lease, с който да се сравни. |
Вторият ред ме стресна. Ако бях вързал нещата по MAC, при първото неплащане скриптът щеше да спре не тази услуга. Бих го разбрал чак когато клиентът се обади.
Решението: IPv4 адресът в коментара
Направих връзката изрична и скучна: всеки binding започва коментара си с IPv4 адреса на клиента, например 198.51.100.57 Клиент А. Скриптът прочита адреса и го сверява със същия списък, по който спира IPv4. Binding без адрес в коментара не се пипа.
Паралелно на клиентските рутери сложих use-interface-duid=yes, за да е DUID-ът предвидим. Тук има капан: щом DUID-ът се смени, статичният binding вече не познава клиента и той остава без IPv6, докато не се смени DUID-ът и на граничния рутер. Редът е: смяна на клиента → смяна на binding-а → renew.
Какво още не е направено. Спирането на IPv6 при неплащане засега е само подготвено. Коментарите са сложени, но скриптът още не пипа binding-ите. Преди това трябва да се провери какво точно прави
disableна binding: маха ли маршрута веднага и какво става с префикса, който клиентският рутер пази до изтичане на lease-а.
В края на първия ден имах префикси при първите клиенти, работещ DNS и план за билинга. Мислех, че най-трудното е минало. В следващата част клиентският рутер ми показа колко греша. IAID-ът не се вижда никъде в конфигурацията. pool-prefix-length=68 ми даде грешка, която не очаквах. А един клиент след рестарт не можеше да вземе префикс, въпреки че всичко изглеждаше наред.
Всички части от поредицата
- Част 1: /60 за всеки клиент и връзката с IPv4 билинга — как граничният рутер раздава префикси, DNS през DHCPv6 и защо не по MAC
- Част 2: IAID, pool 68 и заклещеният NDP — капаните в клиентския рутер
- Част 3: Когато IPv6 се губи по пътя — радиа с IGMP snooping без querier и ONU-та, през които не минава
- Част 4: Два неканени гости — DHCPv6 в мениджмънта на радиолинк, IGMP querier от чужд VLAN и чеклист