Почему OnLinkPrefixLength отличается от адаптера PrefixLength? - PullRequest
0 голосов
/ 03 июля 2011

Если вы возьмете пример MSDN внутри IP_ADAPTER_ADDRESSES Структура в Windows 7 с пакетом обновления 1 (SP1), то разверните перечисление одноадресных адресов:

char s[1024];
for (i = 0; pUnicast != NULL; i++) {
  inet_ntop (pUnicast->Address.lpSockaddr->sa_family,
      pUnicast->Address.lpSockaddr->sa_family == AF_INET ?
      (PVOID)&((struct sockaddr_in*)pUnicast->Address.lpSockaddr)->sin_addr :
      (PVOID)&((struct sockaddr_in6*)pUnicast->Address.lpSockaddr)->sin6_addr,
      s, sizeof (s));
  printf ("\t#%lu %s/%u\n",
      i, s, (unsigned)pUnicast->OnLinkPrefixLength);
  pUnicast = pUnicast->Next;
}

и префиксные данные:

char s[1024];
for (i = 0; pPrefix != NULL; i++) {
  inet_ntop (pPrefix->Address.lpSockaddr->sa_family,
      pPrefix->Address.lpSockaddr->sa_family == AF_INET ?
      (PVOID)&((struct sockaddr_in*)pPrefix->Address.lpSockaddr)->sin_addr :
      (PVOID)&((struct sockaddr_in6*)pPrefix->Address.lpSockaddr)->sin6_addr,
      s, sizeof (s));
  printf ("\t#%lu %s/%u\n",
      i, s, pPrefix->PrefixLength);
  pPrefix = pPrefix->Next;
}

Но один адаптер показывает следующий вывод:

Length of the IP_ADAPTER_ADDRESS struct: 376
IfIndex (IPv4 interface): 15
Adapter name: {84C25EC1-7ABB-4D6E-B8C7-8DEE08961EE2}
#0 2001:0:4137:9e76:2443:d6:ba87:1a2a/64
#1 fe80::2443:d6:ba87:1a2a/64
Number of Unicast Addresses: 2
...
#0 ::/0
#1 2001::/32
#2 2001:0:4137:9e76:2443:d6:ba87:1a2a/128
#3 fe80::/64
#4 fe80::2443:d6:ba87:1a2a/128
#5 ff00::/8
Number of IP Adapter Prefix entries: 6

Список префиксов верен, хотя и немного расширен по описанию MSDN 3 адресов:

В Windows Vista и более поздних версиях,связанные структуры IP_ADAPTER_PREFIX, на которые указывает член FirstPrefix, включают три префикса IP-адаптера для каждого IP-адреса, назначенного адаптеру.К ним относятся префикс IP-адреса хоста, префикс IP-адреса подсети и префикс широковещательного IP-адреса подсети.Кроме того, для каждого адаптера есть префикс адреса многоадресной рассылки и префикс широковещательного адреса.

Я определяю, что список правильный, сравнивая с выводом netstat -r:

IPv6 Route Table
==================================================
Active Routes:
 If Metric Network Destination      Gateway
 15     58 ::/0                     On-link
  1    306 ::1/128                  On-link
 15     58 2001::/32                On-link
 15    306 2001:0:4137:9e76:2443:d6:ba87:1a2a/128
                                    On-link
 14    281 fe80::/64                On-link
 15    306 fe80::/64                On-link
 15    306 fe80::2443:d6:ba87:1a2a/128
                                    On-link
 14    281 fe80::6153:a573:f691:8167/128
                                    On-link
  1    306 ff00::/8                 On-link
 15    306 ff00::/8                 On-link
 14    281 ff00::/8                 On-link
==================================================

Однако моя интерпретация API заключается в том, что OnLinkPrefixLength должен возвращать 32 для одноадресного адреса глобальной области, а API только для Vista + возвращает 64, почему?

1 Ответ

1 голос
/ 05 июля 2011

Немного справочной информации: Существует несколько длин префиксов по умолчанию для IPv6.ЛВС обычно имеет длину префикса 64. Локальные адреса ссылок, которые вы видите (fe80 :: / 64), являются примерами этого.Адреса вашей собственной системы отображаются в таблице маршрутизации как отдельные адреса (/ 128).Адреса многоадресной рассылки являются специальными (ff00 :: / 8), поскольку они соответствуют не одному адресу одного хоста, а группе из нескольких хостов в потенциально нескольких сетях.

Вы видите / 32 /Адресный блок Teredo (2001: 0000 :: / 32 == 2001 :: / 32).Teredo - это протокол туннелирования IPv6-in-IPv4, который автоматически настраивается Windows.Таблица маршрутизации показывает, что ваш маршрут IPv6 по умолчанию (:: / 0) проходит через адаптер Teredo.Похоже, что ваша система не имеет «обычного» глобального одноадресного IPv6.

Сводка: Длина префикса по ссылке обычно равна / 64.Teredo является особым случаем и использует фиксированный «special» / 32.Ваши собственные адреса IPv6 полны и имеют префикс длины /128.

. Вы правы в том, что 2001: 0: 4137: 9e76: 2443: d6: ba87: 1a2a / 64 не имеет смысла.Это Teredo, поэтому длина сетевого префикса должна быть равна / 32.Если это один адрес IPv6, он должен иметь длину префикса / 128./ 64 не имеет смысла для Teredo и кажется ошибкой.

...