UNIX: разработка сетевых приложений, стр. 203
Создание маршрутизирующего сокета
17AF_ROUTEЗаполнение структуры rt_msghdr
18-25rt_msghdrЗаполнение структуры адреса сокета адресом получателя
26-29rt_msghdrsockaddr_inЗапись сообщения ядру (функция write) и чтение ответа (функция read)
30-34writeВторая часть этой программы показана в листинге 18.4. Она обрабатывает ответ.
Листинг 18.4. Вторая часть программы, запускающая команду RTM_GET на маршрутизирующем сокете
//route/getrt.c35 rtm = (struct rt_msghdr*)buf;36 sa = (struct sockaddr*)(rtm + 1);37 get_rtaddrs(rtm->rtm_addrs, sa, rti_info);38 if ((sa = rti_infо[RTAX_DST]) != NULL)39 printf("dest: %s\n", Sock_ntop_host(sa, sa->sa_len));40 if ((sa = rti_infо[RTAX_GATEWAY]) != NULL)41 printf("gateway: %s\n", Sock_ntop_host(sa, sa->sa_len));42 if ((sa = rti_info[RTAX_NETMASK]) != NULL)43 printf("netmask: %s\n", Sock_masktop(sa, sa->sa_len));44 if ((sa = rti_info[RTAX_GENMASK]) != NULL)45 printf("genmask: %s\n", Sock_masktop(sa, sa->sa_len));46 exit(0);47 }34-35rtmrt_msghdrsa36rtm_addrsrt_msghdrget_rtaddrssarti_inforti_info
Рис. 18.2. Структура rti_info, заполненная с помощью нашей функции get_rtaddrs
Затем наша программа проходит массив
rti_info37-44sock_ntop_hostsock_masktopВ листинге 18.5 показана наша функция
get_rtaddrsЛистинг 18.5. Создание массива указателей на структуры адреса сокета в маршрутизирующем сообщении
//libroute/get_rtaddrs.c 1 #include "unproute.h" 2 /* 3 * Округляем 'а' до следующего значения, кратного 'size' 4 */ 5 #define ROUNDUP(a, size) (((a) & ((size)-1)) ? (1 + ((a) | ((size)-1))) : (a)) 6 /* Переходим к следующей структуре адреса сокета. 7 * Если sa_len равно 0, это значит, что 8 * размер выражен числом типа u_long). 9 */10 #define NEXT_SA(ap) ар = (SA*) \11 ((caddr_t)ар + (ap->sa_len ? ROUNDUP(ap->sa_len, sizeof(u_long)) : \12 sizeof(u_long)))13 void14 get_rtaddrs(int addrs, SA *sa, SA **rti_info)15 {16 int i;17 for (i = 0; i < RTAX_MAX; i++) {18 if (addrs & (1 << i)) {19 rti_info[i] = sa;20 NEXT_SA(sa);21 } else22 rti_info[1] = NULL;23 }24 }Цикл по восьми возможным указателям
Значение
RTAX_MAXRTA_xxxrtm_addrsifm_addrsifam_addrsrti_info