From: Amos Jeffries Date: Sat, 15 Nov 2008 03:28:44 +0000 (-0700) Subject: Fix IPAddress not setting sin_len on BSD X-Git-Tag: SQUID_3_2_0_1~1332 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=1ef0b9cefc7c34fdaec763a913e92ce1fa3f5218;p=thirdparty%2Fsquid.git Fix IPAddress not setting sin_len on BSD --- diff --git a/lib/IPAddress.cc b/lib/IPAddress.cc index 9797739abd..0cc269da32 100644 --- a/lib/IPAddress.cc +++ b/lib/IPAddress.cc @@ -37,8 +37,9 @@ */ #include "config.h" - #include "IPAddress.h" +#include "util.h" + #if HAVE_ASSERT_H #include @@ -53,8 +54,6 @@ #include /* inet_ntoa() */ #endif -#include "util.h" - #ifdef INET6 #error "INET6 defined but has been deprecated! Try running bootstrap and configure again." #endif @@ -1099,43 +1098,17 @@ void IPAddress::GetSockAddr(struct sockaddr_storage &addr, const int family) con #if USE_IPV6 if ( family == AF_INET6 || (family == AF_UNSPEC && IsIPv6()) ) { - memcpy(&addr, &m_SocketAddr, sizeof(struct sockaddr_in6)); - if (addr.ss_family == 0) { - addr.ss_family = AF_INET6; - } -#if HAVE_SS_LEN_IN_SS - /* not all OS have this field, BUT when they do it can be a problem if set wrong */ - addr.ss_len = htons(sizeof(struct sockaddr_in6)); -#elif HAVE_SIN6_LEN_IN_SAI - ((struct sockaddr_in6*)&addr)->sin6_len = htons(sizeof(struct sockaddr_in6)); -#endif + struct sockaddr_in6 *ss6 = (struct sockaddr_in6*)&addr; + GetSockAddr(*ss6); } else if ( family == AF_INET || (family == AF_UNSPEC && IsIPv4()) ) { sin = (struct sockaddr_in*)&addr; - addr.ss_family = AF_INET; - sin->sin_port = m_SocketAddr.sin6_port; - Map6to4( m_SocketAddr.sin6_addr, sin->sin_addr); -#if HAVE_SS_LEN_IN_SS - /* not all OS have this field, BUT when they do it can be a problem if set wrong */ - addr.ss_len = htons(sizeof(struct sockaddr_in)); -#elif HAVE_SIN_LEN_IN_SAI - sin->sin_len = htons(sizeof(struct sockaddr_in)); -#endif + GetSockAddr(*sin); } else { IASSERT("false",false); } #else /* not USE_IPV6 */ sin = (struct sockaddr_in*)&addr; - memcpy(sin, &m_SocketAddr, sizeof(struct sockaddr_in)); - - addr.ss_family = AF_INET; - -#if HAVE_SS_LEN_IN_SS - /* not all OS have this field, BUT when they do it can be a problem if set wrong */ - addr.ss_len = htons(sizeof(struct sockaddr_in)); -#elif HAVE_SIN_LEN_IN_SAI - sin->sin_len = htons(sizeof(struct sockaddr_in)); -#endif - + GetSockAddr(*sin); #endif /* USE_IPV6 */ } @@ -1165,7 +1138,7 @@ void IPAddress::GetSockAddr(struct sockaddr_in &buf) const { #if HAVE_SIN_LEN_IN_SAI /* not all OS have this field, BUT when they do it can be a problem if set wrong */ - buf.sin_len = htons(sizeof(struct sockaddr_in)); + buf.sin_len = sizeof(struct sockaddr_in); #endif } @@ -1177,9 +1150,11 @@ void IPAddress::GetSockAddr(struct sockaddr_in6 &buf) const { /* maintain address family. It may have changed inside us. */ buf.sin6_family = AF_INET6; +assert(HAVE_SIN6_LEN_IN_SAI); + #if HAVE_SIN6_LEN_IN_SAI /* not all OS have this field, BUT when they do it can be a problem if set wrong */ - buf.sin6_len = htons(sizeof(struct sockaddr_in6)); + buf.sin6_len = sizeof(struct sockaddr_in6); #endif } diff --git a/lib/tests/testIPAddress.cc b/lib/tests/testIPAddress.cc index 431f31907c..b96122fc6a 100644 --- a/lib/tests/testIPAddress.cc +++ b/lib/tests/testIPAddress.cc @@ -91,6 +91,9 @@ testIPAddress::testSockAddrConstructor() insock.sin_family = AF_INET; insock.sin_port = htons(80); insock.sin_addr.s_addr = htonl(0xC0A8640C); +#if HAVE_SIN_LEN_IN_SAI + insock.sin_len = sizeof(struct sockaddr_in); +#endif IPAddress anIPA((const struct sockaddr_in)insock); @@ -121,6 +124,9 @@ testIPAddress::testSockAddr6Constructor() insock.sin6_addr.s6_addr32[1] = htonl(0x00000000); insock.sin6_addr.s6_addr32[2] = htonl(0x0000FFFF); insock.sin6_addr.s6_addr32[3] = htonl(0xC0A8640C); +#if HAVE_SIN6_LEN_IN_SAI + insock.sin6_len = sizeof(struct sockaddr_in6); +#endif IPAddress anIPA((const struct sockaddr_in6)insock); @@ -149,6 +155,9 @@ testIPAddress::testCopyConstructor() insock.sin_family = AF_INET; insock.sin_port = htons(80); insock.sin_addr.s_addr = htonl(0xC0A8640C); +#if HAVE_SIN_LEN_IN_SAI + insock.sin_len = sizeof(struct sockaddr_in); +#endif IPAddress inIPA(insock); IPAddress outIPA(inIPA); @@ -402,6 +411,10 @@ testIPAddress::testToURL_fromSockAddr() sock.sin_addr.s_addr = htonl(0xC0A8640C); sock.sin_port = htons(80); sock.sin_family = AF_INET; +#if HAVE_SIN_LEN_IN_SAI + sock.sin_len = sizeof(struct sockaddr_in); +#endif + IPAddress anIPA(sock); char buf[MAX_IPSTRLEN]; @@ -420,6 +433,9 @@ testIPAddress::testToURL_fromSockAddr() ip6val.sin6_addr.s6_addr32[3] = htonl(0xFFFFFFFF); ip6val.sin6_port = htons(80); ip6val.sin6_family = AF_INET6; +#if HAVE_SIN6_LEN_IN_SAI + ip6val.sin6_len = sizeof(struct sockaddr_in6); +#endif IPAddress bnIPA(ip6val); @@ -581,6 +597,7 @@ testIPAddress::testAddrInfo() anIP.GetAddrInfo(ipval); +#if 0 /* display a byte-by-byte hex comparison of the addr cores */ unsigned int *p; p = (unsigned int*)expect; @@ -591,6 +608,7 @@ testIPAddress::testAddrInfo() printf("\nSQD-ADDRINFO: %2x %2x %2x %2x %2x %2x", p[0],p[1],p[2],p[3],p[4],p[5] ); printf("\n"); +#endif /*0*/ // check the addrinfo object core. (BUT not the two ptrs at the tail) // details @@ -598,21 +616,26 @@ testIPAddress::testAddrInfo() CPPUNIT_ASSERT_EQUAL( expect->ai_family, ipval->ai_family ); // check the sockaddr it points to. CPPUNIT_ASSERT_EQUAL( expect->ai_addrlen, ipval->ai_addrlen ); + +#if 0 p = (unsigned int*)(expect->ai_addr); - printf("\nSYS-ADDR: (%d) %2x %2x %2x %2x %2x %2x %2x %2x", + printf("\nSYS-ADDR: (%d) %x %x %x %x %x %x %x %x ...", expect->ai_addrlen, p[0],p[1],p[2],p[3],p[4],p[5],p[6],p[7] ); p = (unsigned int*)(ipval->ai_addr); - printf("\nSQD-ADDR: (%d) %2x %2x %2x %2x %2x %2x %2x %2x", + printf("\nSQD-ADDR: (%d) %x %x %x %x %x %x %x %x ...", ipval->ai_addrlen, p[0],p[1],p[2],p[3],p[4],p[5],p[6],p[7] ); printf("\n"); - -#if USE_IPV6 #if HAVE_SS_LEN_IN_SS printf("\nSYS SS_LEN=%d\nSQD SS_LEN=%d\n",((struct sockaddr_storage*)expect->ai_addr)->ss_len, ((struct sockaddr_storage*)ipval->ai_addr)->ss_len ); +#endif +#endif /*0*/ + +#if USE_IPV6 +#if HAVE_SS_LEN_IN_SS CPPUNIT_ASSERT_EQUAL( ((struct sockaddr_storage*)expect->ai_addr)->ss_len, ((struct sockaddr_storage*)ipval->ai_addr)->ss_len ); CPPUNIT_ASSERT_EQUAL( (socklen_t)((struct sockaddr_storage*)ipval->ai_addr)->ss_len, ipval->ai_addrlen ); @@ -621,6 +644,11 @@ testIPAddress::testAddrInfo() CPPUNIT_ASSERT_EQUAL( ((struct sockaddr_in6*)expect->ai_addr)->sin6_len, ((struct sockaddr_in6*)ipval->ai_addr)->sin6_len ); CPPUNIT_ASSERT_EQUAL( (socklen_t)((struct sockaddr_in6*)ipval->ai_addr)->sin6_len, ipval->ai_addrlen ); +#endif +#if HAVE_SIN_LEN_IN_SAI + CPPUNIT_ASSERT_EQUAL( ((struct sockaddr_in*)expect->ai_addr)->sin_len, + ((struct sockaddr_in*)ipval->ai_addr)->sin_len ); + CPPUNIT_ASSERT_EQUAL( (socklen_t)((struct sockaddr_in*)ipval->ai_addr)->sin_len, ipval->ai_addrlen ); #endif CPPUNIT_ASSERT_EQUAL( ((struct sockaddr_in6*)expect->ai_addr)->sin6_family, ((struct sockaddr_in6*)ipval->ai_addr)->sin6_family ); @@ -628,8 +656,6 @@ testIPAddress::testAddrInfo() ((struct sockaddr_in6*)ipval->ai_addr)->sin6_port ); #else #if HAVE_SS_LEN_IN_SS - printf("\nSYS SS_LEN=%d\nSQD SS_LEN=%d\n",((struct sockaddr_storage*)expect->ai_addr)->ss_len, - ((struct sockaddr_storage*)ipval->ai_addr)->ss_len ); CPPUNIT_ASSERT_EQUAL( ((struct sockaddr_storage*)expect->ai_addr)->ss_len, ((struct sockaddr_storage*)ipval->ai_addr)->ss_len ); CPPUNIT_ASSERT_EQUAL( (socklen_t)((struct sockaddr_storage*)ipval->ai_addr)->ss_len, ipval->ai_addrlen );