Deduplicate results of getaddrinfo before binding
Sometimes it contains duplicates (from our POV, probably different in
some details but it doesn't matter), must not cause weird behavior of
application.
Eduard Bloch
7 years ago
16 | 16 | #include <cstdio> |
17 | 17 | #include <list> |
18 | 18 | #include <map> |
19 | #include <unordered_set> | |
19 | 20 | #include <iostream> |
20 | 21 | #include <algorithm> // std::min_element, std::max_element |
21 | 22 | |
256 | 257 | |
257 | 258 | struct addrinfo *res, *p; |
258 | 259 | if(0!=getaddrinfo(addi, port.c_str(), &hints, &res)) |
259 | { | |
260 | perror("Error resolving address for binding"); | |
261 | return; | |
262 | } | |
263 | ||
260 | { | |
261 | perror("Error resolving address for binding"); | |
262 | return; | |
263 | } | |
264 | ||
265 | std::unordered_set<std::string> dedup; | |
264 | 266 | for(p=res; p; p=p->ai_next) |
265 | 267 | { |
268 | if(p->ai_family != AF_INET6 && p->ai_family != AF_INET) | |
269 | continue; | |
270 | ||
271 | // processed before? | |
272 | if(!dedup.insert(std::string((LPCSTR)p->ai_addr, p->ai_addrlen)).second) | |
273 | continue; | |
274 | ||
266 | 275 | int nSockFd = socket(p->ai_family, p->ai_socktype, p->ai_protocol); |
267 | 276 | if (nSockFd<0) |
268 | 277 | goto error_socket; |