Некоторое время назад в комментариях к статье "IPv6 шлюз для локальной сети" меня попросили рассказать о том, как я активировал IPv6 в одном из своих проектов. Начну с пары слов о самом проекте. CareNet - это результат кооперации двух крупных Шведских университетов: KTH Royal Institute of Technology и Karolinska Institutet. Вкратце, CareNet - это система, позволяющая наблюдать паллиативных пациентов вне больницы. У пациента дома устанавливается небольшое устройство, которое имеет доступ в Интернет и подключено посредством VPN к серверам CareNet. Устройство включает в себя HDVC-клиент, набор сенсоров для контроля состояния пациента и средства доступа к медицинскому порталу, содержащему всю информацию о пациенте. Медицинская информация доступна как самому пациенту, так и доктору.
Но статья об активации IPv6, поэтому нам более интересна не клиентская, а центральная часть инфраструктуры CareNet. Она включает в себя ряд маршрутизаторов и серверов, которые расположены на университетской площадке KTH в Стокгольме. Схема дает преставление о масштабах сети.
На протяжении 20 недель моей задачей было поддерживать указанную инфраструктуру в рабочем состоянии и наращивать ее функционал. Одним из заданий я для себя определил активацию IPv6 в этой небольшой сетевой топологии. Более того, помимо развертывания IPv6 внутри сети, хотелось также подключить CareNet к глобальному IPv6 пространству.
Адресация
Начал я с того, что попросил администрацию университета выделить мне кусочек лабораторного диапазона IPv6 для своей небольшой песочницы. Мне был торжественно делегирован префикс 2001:6b0:32::/49. Поначалу я обижался и несколько раз хотел бежать и просить еще, но в итоге, прибросив схему адресации так и этак на бумаге, я решил что 6x1023 адресов должно хватить.
Определившись с адресацией, я настроил интерфейсы на маршрутизаторах. Здесь необходимо сказать, что маршрутизаторы в CareNet необычные, построенные на базе высокопроизводительной аппаратно-программной Linux-платформы Bifrost. Это университетская разработка выходящая сейчас на коммерческий рынок. Интерфейсы между маршрутизаторами имеют пропускную способность 10 Гбит/с. За маршрутизацию (control plane) отвечает программный пакет Quagga.
Внутренняя маршрутизация, OSPFv3
Добавив IPv6 адреса на интерфейсы маршрутизаторов я запустил OSPFv3 в качестве динамического протокола маршрутизации. Настройки базовые, одна OSPF-зона 0.0.0.0. Технического объяснения почему выбран OSPF не будет. Лично я выбираю по названию. RIPng мне не нравится. Вот IS-IS с удовольствием, но Quagga его не поддерживает.
С пакетом Quagga работал впервые, но освоился моментально потому что командный интерфейс аналогичен Cisco CLI. Пример конфигурации демона ospf6d привожу для двух маршрутизаторов:
hostname VR-ospf6d
!
router ospf6
router-id 192.16.126.9
interface eth1 area 0.0.0.0 #интерфейс в сторону маршрутизатора HR
interface eth2 area 0.0.0.0 #интерфейс в сторону маршрутизатора KR
interface dummy0 area 0.0.0.0 #loopback
!
hostname KR-ospf6d
!
interface eth2 #интерфейс в сторону клиентов и серверной фермы
ipv6 ospf6 passive #деактивация сообщений OSPF Hello
!
router ospf6
router-id 192.16.126.10
interface eth2 area 0.0.0.0 #интерфейс в сторону клиентов и серверной фермы
interface eth0 area 0.0.0.0 #интерфейс в сторону маршрутизатора VR
interface dummy0 area 0.0.0.0
!
Динамическое выделение адресов, DHCPv6
Маршрутизация активирована и следующим возник вопрос о динамическом выделении IPv6-адресов серверам в ферме и клиентам в сетях доступа. Эту задачу решено было возложить на DHCPv6 сервер. Я развернул два DHCPv6-сервера: ISC DHCP и Dibbler. Был организован конкурс по условиям которого тот из серверов, кто первым обслужит клиента выделив ему IPv6 адрес, останется функционировать. Dibbler оказался расторопнее, поэтому ISC DHCP был уничтожен. Пример настройки диапазонов выделяемых адресов:
vp@dns:~$ cat /etc/dibbler/server.conf
...
option dns-server 2001:6b0:32:0::66 #IPv6 адрес сервера DNS
class {
pool 2001:6b0:32:0::0000 - 2001:6b0:32:0::0fff #диапазон выделяемых адресов IPv6
}
client duid 0x000100011657fdc9be10f563c5bf {
address 2001:6b0:32:0::69 #статический адрес Ipv6 для сервера SIP
}
...
Два интересных отличия от привычного DHCP для IPv4:
Во-первых, DHCPv6 не предоставляет клиенту адрес шлюза по умолчанию (default gateway), которым в нашем случае является маршрутизатор в Kista. Объявить о своем существовании должен сам шлюз в соответствии с механизмом Neighbor Discovery. RFC 2461 подробно описывает этот механизм, я лишь упомяну что маршрутизатор должен периодически отправлять сообщение Router Advertisement (RA), объявляя себя шлюзом по умолчанию в данном сегменте. В моем случае для этого необходимо было дополнить конфигурацию маршрутизатора KR:
hostname KR-zebra
!
interface eth2 #интерфейс в сторону клиентов и серверной фермы
no ipv6 nd suppress-ra #не подавлять сообщения RA
ipv6 nd prefix 2001:6b0:32::/64 no-autoconfig #IPv6 префикс для сегмента
!
Вторая особенность заключается в том, на каком основании DHCPv6-сервер выделяет статические адреса. Если в DHCPv4 достаточно было просто задать MAC-адрес устройства которому надо выделить постоянный адрес, то в конфигурации сервера DHCPv6 придется прописать так называемый DHCP Unique Identifier (DUID). Предлагаю найти его в приведенной ранее конфигурации самостоятельно. Об идентификаторе DUID можно почитать в RFC 3315.
Внешняя маршрутизация, BGP
Внутренняя маршрутизация функционирует, клиенты получили адреса, дело за малым - открыть IPv6 доступ в интернет. Догадываясь о том, что мой непосредственный сосед - AS 2839 (KTH-LAN) уже является частью глобального IPv6 пространства, я осмелился просить его администраторов разрешить мне установить с KTH-LAN дополнительную сессию BGP для объявления моего префикса IPv6. После согласования всех технических деталей соседство IPv6 BGP было установлено. Пара дней ушла на то, чтобы убедить автономную систему следующую далее по цепочке (SUNET) обновить свои входящие BGP-фильтры и наконец выпустить мой префикс в свободное плавание. Конфигурация демона bgpd:
Помимо фильтрации объявляемых и принимаемых префиксов неплохо было бы активировать идентичные фильтры непосредственно для пересекающего границу автономной системы трафика, как механизм противодействия атакам "IP spoofing". Простой список контроля доступа ACL вполне справится с этой задачей.
Настроив BGP и разобравшись с фильтрами, открыл шампанское и приготовился встречать первый ICMPv6 ответ, более известный как ping, от ipv6.google.com. Трассировка маршрута ниже:
vp@dns:~$ traceroute6 ipv6.google.com
traceroute to ipv6.l.google.com (2a00:1450:4010:c01::93) from 2001:6b0:32::66, 30 hops max, 24 byte packets
1 kis-lanlink.carenet-se.se (2001:6b0:32::1) 1.13 ms 0.457 ms 0.49 ms
2 lpp01m02-in-x93.1e100.net (2a00:1450:4010:c01::93) 0.944 ms 0.933 ms 1.115 ms
3 br1g-cn6-p2p.gw.kth.se (2001:6b0:1:2::1) 1.261 ms 1.3 ms 1.091 ms
4 * * *
5 t1fre-ae5-v1.sunet.se (2001:6b0:1e:1::36) 1.467 ms 1.256 ms 1.239 ms
6 se-fre.nordu.net (2001:948:0:f051::1) 1.718 ms 1.562 ms 1.463 ms
7 se-tug.nordu.net (2001:948:1:1::3) 1.344 ms 1.315 ms 1.269 ms
8 se-tug2.nordu.net (2001:948:1:5::3) 1.505 ms 1.359 ms 1.287 ms
9 google-gw.nordu.net (2001:948:0:f008::3) 1.443 ms 1.616 ms 1.298 ms
10 2001:4860::1:0:26ec (2001:4860::1:0:26ec) 1.896 ms 2.002 ms 1.911 ms
11 2001:4860::8:0:26e5 (2001:4860::8:0:26e5) 41.025 ms 11.119 ms 11.02 ms
12 2001:4860::2:0:2aaf (2001:4860::2:0:2aaf) 11.223 ms 11.455 ms 11.955 ms
13 2001:4860:0:1::4d0 (2001:4860:0:1::4d0) 22.558 ms 21.472 ms 17.857 ms
14 lpp01m02-in-x93.1e100.net (2a00:1450:4010:c01::93) 10.833 ms 10.878 ms 13.669 ms
DNS для IPv6
Напоследок расскажу как был настроен DNS для работы с адресами IPv6. Устанавливать DNS сервер с нуля не потребовалось, потому что в сети уже имелся сервер BIND, обслуживающий диапазон IPv4. В прямую DNS-зону к уже имеющимся адресам IPv4 были добавлены записи IPv6. Довольно прямолинейно и просто, но на всякий случай приведу пример конфигурации:
vp@dns:~$ sudo cat /etc/bind/zones/external/carenet-se.se.db
...
;; Routers' loopacks
vr IN A 192.16.126.9
vr IN AAAA 2001:6b0:32:10::1
...
А вот с обратной зоной (reverse DNS lookup) пришлось повозиться. Был создан отдельный файл, названный в соответствии с канонами 2.3.0.0.0.b.6.0.1.0.0.2.ip6.arpa. Название образовано из префикса 2001:6b0:32::/49 записанного в обратном порядке и дополненного нулями. Далее в достаточно недружелюбном и трудном к восприятию формате добавлены обратные DNS-записи для всех IPv6-систем в сети. Часть конфигурации приведена ниже:
vp@dns:~$ sudo cat /etc/bind/zones/2.3.0.0.0.b.6.0.1.0.0.2.ip6.arpa
$TTL 600
$ORIGIN 2.3.0.0.0.b.6.0.1.0.0.2.ip6.arpa. #маска
@ IN SOA ns.carenet-se.se. adm.carenet-se.se. (
2011120101;
28800;
604800;
604800;
86400);
IN NS ns.carenet-se.se.
IN NS ns.ssvl.kth.se.
IN NS ns2.ssvl.kth.se.
6.6.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0 IN PTR ns.carenet-se.se.
...
$ORIGIN 0.0.0.0.2.3.0.0.0.b.6.0.1.0.0.2.ip6.arpa.
9.6.0.0.0.0.0.0.0.0.0.0.0.0.0.0 IN PTR sip.carenet-se.se.
4.9.0.0.0.0.0.0.0.0.0.0.0.0.0.0 IN PTR log.carenet-se.se.
...
$ORIGIN 0.1.0.0.2.3.0.0.0.b.6.0.1.0.0.2.ip6.arpa.
1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0 IN PTR vr.carenet-se.se.
...
Заключение и дополнительная информация
Поставленная задача достигнута, сеть CareNet стала частью глобального IPv6 домена. Подробно весь процесс активации IPv6 я описал в официальных документах к проекту, которые доступны на сайте CareNet. Там же можно найти и схемы. Проект академический, информация открыта и никакой тайны в себе не содержит. Спасибо за внимание.
Иcтoчник