Я поддерживаю GPSD, широко распространенный сервисный демон с открытым исходным кодом, который отслеживает GPS и другие геодезические датчики. Он прослушивает соединения клиентских приложений через порт 2947 как на IPv4, так и на IPv6. В целях безопасности и конфиденциальности он обычно прослушивает только адрес обратной связи, но есть опция -G для демона, которая предназначена для того, чтобы заставить его прослушивать любой адрес.
Проблема: опция -G работает в IPv4, но я не могу понять, как заставить ее работать с IPv6. Метод, который должен работать на основе различных учебных примеров, не работает, вместо этого выдается ошибка, указывающая, что адрес уже используется. Мне нужна помощь, чтобы исправить это от людей, имеющих опыт программирования в сети IPv6.
Соответствующий код на http://git.berlios.de/cgi-bin/gitweb.cgi?p=gpsd;a=blob;f=gpsd.c;h=ee2156caf03ca23405f57f3e04e9ef306a75686f;hb=HEAD
Этот код работает правильно как в случаях -G, так и в случаях не -G в IPv4, что легко проверить с помощью netstat -l.
Теперь посмотрите вокруг строки 398 после "case AF_INET6:". Параметр listen_global устанавливается с помощью -G; если false, код успешно выполняется. В настоящее время существует следующий комментарий, унаследованный от неизвестного участника, который выглядит следующим образом:
/* else */
/* BAD: sat.sa_in6.sin6_addr = in6addr_any;
* the simple assignment will not work (except as an initializer)
* because sin6_addr is an array not a simple type
* we could do something like this:
* memcpy(sat.sa_in6.sin6_addr, in6addr_any, sizeof(sin6_addr));
* BUT, all zeros is IPv6 wildcard, and we just zeroed the array
* so really nothing to do here
*/
Согласно различным учебным примерам, которые я посмотрел, задание "sat.sa_in6.sin6_addr = in6addr_any;" (несмотря на комментарий) правильно, и он компилируется. Тем не менее, запуск с -G не удается, утверждая, что адрес прослушивания уже используется.
Является ли задание "sat.sa_in6.sin6_addr = in6addr_any;" номинально правильно здесь? Что еще, если что, я пропускаю?