X-Git-Url: http://plrg.eecs.uci.edu/git/?p=folly.git;a=blobdiff_plain;f=folly%2FIPAddressV6.cpp;h=3490669dcbdd72db0cf2484c24e3e6708c045970;hp=29450f4b08ac6c35c5a7ee398343ac1195a75381;hb=e6fa347e7e436f0a52f5e313f55b7d1ef47a3767;hpb=9b6eade1f3afa32adc9f7d56739b119f53168ccb diff --git a/folly/IPAddressV6.cpp b/folly/IPAddressV6.cpp index 29450f4b..3490669d 100644 --- a/folly/IPAddressV6.cpp +++ b/folly/IPAddressV6.cpp @@ -25,6 +25,19 @@ #include #include +#if !_WIN32 +#include +#else +// Because of the massive pain that is libnl, this can't go into the socket +// portability header as you can't include and in +// the same translation unit without getting errors -_-... +#include +#include + +// Alias the max size of an interface name to what posix expects. +#define IFNAMSIZ IF_NAMESIZE +#endif + using std::ostream; using std::string; @@ -403,30 +416,36 @@ IPAddressV6 IPAddressV6::mask(size_t numBits) const { // public string IPAddressV6::str() const { - char buffer[INET6_ADDRSTRLEN] = {0}; - sockaddr_in6 sock = toSockAddr(); - int error = getnameinfo( - (sockaddr*)&sock, - sizeof(sock), - buffer, - INET6_ADDRSTRLEN, - nullptr, - 0, - NI_NUMERICHOST); - if (!error) { - string ip(buffer); - return ip; - } else { + char buffer[INET6_ADDRSTRLEN + IFNAMSIZ + 1]; + + if (!inet_ntop(AF_INET6, toAddr().s6_addr, buffer, INET6_ADDRSTRLEN)) { throw IPAddressFormatException(to( "Invalid address with hex ", "'", detail::Bytes::toHex(bytes(), 16), - "%", - sock.sin6_scope_id, "'", - " , with error ", - gai_strerror(error))); + " with error ", + strerror(errno))); } + + auto scopeId = getScopeId(); + if (scopeId != 0) { + auto len = strlen(buffer); + buffer[len] = '%'; + if (!if_indextoname(scopeId, buffer + len + 1)) { + throw IPAddressFormatException(to( + "Invalid scope for address with hex ", + "'", + detail::Bytes::toHex(bytes(), 16), + "%", + scopeId, + "'", + " with error ", + strerror(errno))); + } + } + + return string(buffer); } // public