The given patch will add IPv6 support to nzbget. Both the internal client-server connection and the external connections to an IPv6 newsserver have been successfully tested. For testing, you can use newszilla6.xs4all.nl, which allows 3 simultaneous connections and is open for everyone with an IPv6 connection. Reproducible: Always Actual Results: No IPv6 support Expected Results: IPv6 connection
Created attachment 141875 [details, diff] Patch to add IPv6 support to nzbget
Comment on attachment 141875 [details, diff] Patch to add IPv6 support to nzbget ><HTML><HEAD/><BODY><PRE>diff -Naur nzbget-0.2.3/Connection.cpp nzbget-0.2.3-ipv6/Connection.cpp >--- nzbget-0.2.3/Connection.cpp 2005-09-02 09:00:41.000000000 +0200 >+++ nzbget-0.2.3-ipv6/Connection.cpp 2008-01-27 14:07:32.000000000 +0100 >@@ -255,37 +255,42 @@ > m_iBufferLength = 0; > m_iBufferPos = 0; > >- struct hostent *hinfo; >- >- hinfo = ::gethostbyname( m_pNetAddress->GetHost() ); >- >- if( !hinfo ) >+ int res; >+ >+ struct addrinfo addr_hints, *addr_list, *addr; >+ char iPortStr[sizeof(int) * 4 + 1]; //is enough to hold any converted int >+ >+ memset(&addr_hints, 0, sizeof(addr_hints)); >+ addr_hints.ai_family = AF_UNSPEC; /* Allow IPv4 or IPv6 */ >+ addr_hints.ai_socktype = SOCK_STREAM, >+ >+ sprintf(iPortStr, "%d", m_pNetAddress->GetPort()); >+ >+ res = ::getaddrinfo( m_pNetAddress->GetHost(), iPortStr, &addr_hints, &addr_list ); >+ >+ if( res != 0 ) > { > error( "Could not resolve hostname %s", m_pNetAddress->GetHost() ); > return -1; > } > >- memset(&m_SocketAddress, '\0', sizeof(m_SocketAddress)); >- m_SocketAddress.sin_family = AF_INET; >- memcpy(&m_SocketAddress.sin_addr.s_addr, hinfo->h_addr_list[0], sizeof(m_SocketAddress.sin_addr.s_addr)); >- m_SocketAddress.sin_port = htons( m_pNetAddress->GetPort() ); >- >- m_iSocket = ::socket(PF_INET,SOCK_STREAM,0); >- >- if( m_iSocket < 0 ) >- { >- error("Socket creation failed for %s!", m_pNetAddress->GetHost() ); >- return -1; >- } >- >- int res = ::connect( m_iSocket ,(struct sockaddr *) &m_SocketAddress, sizeof(m_SocketAddress) ); >- >- if (res < 0) >+ for (addr = addr_list; addr != NULL; addr = addr->ai_next) >+ { >+ m_iSocket = ::socket(addr->ai_family, addr->ai_socktype, addr->ai_protocol); >+ if (m_iSocket == -1) continue; >+ >+ res = ::connect( m_iSocket , addr->ai_addr, addr->ai_addrlen ); >+ if (res != -1) break; /* Connection established */ >+ } >+ >+ if( addr == NULL ) > { >- error("Connection to %s failed!", m_pNetAddress->GetHost() ); >+ error("Socket creation or connection failed for %s!", m_pNetAddress->GetHost() ); > return -1; > } > >+ freeaddrinfo( addr_list ); /* No longer needed */ >+ > m_pFileBuffer = fdopen( m_iSocket, "r+" ); > > if( !m_pFileBuffer ) >@@ -339,34 +344,42 @@ > { > debug("Connection::DoBind()"); > >- struct hostent *hinfo; >- >- hinfo = ::gethostbyname( m_pNetAddress->GetHost() ); >- >- if( !hinfo ) >+ int res; >+ >+ struct addrinfo addr_hints, *addr_list, *addr; >+ char iPortStr[sizeof(int) * 4 + 1]; //is enough to hold any converted int >+ >+ memset(&addr_hints, 0, sizeof(addr_hints)); >+ addr_hints.ai_family = AF_UNSPEC; /* Allow IPv4 or IPv6 */ >+ addr_hints.ai_socktype = SOCK_STREAM, >+ addr_hints.ai_flags = AI_PASSIVE; /* For wildcard IP address */ >+ >+ sprintf(iPortStr, "%d", m_pNetAddress->GetPort()); >+ >+ res = ::getaddrinfo( m_pNetAddress->GetHost(), iPortStr, &addr_hints, &addr_list ); >+ >+ if( res != 0 ) > { > error( "Could not resolve hostname %s", m_pNetAddress->GetHost() ); > return -1; > } > >- m_iSocket = ::socket( PF_INET, SOCK_STREAM, 0 ); >- >- if( m_iSocket < 0 ) >+ for (addr = addr_list; addr != NULL; addr = addr->ai_next) >+ { >+ m_iSocket = ::socket(addr->ai_family, addr->ai_socktype, addr->ai_protocol); >+ if (m_iSocket == -1) continue; >+ >+ res = ::bind( m_iSocket , addr->ai_addr, addr->ai_addrlen ); >+ if (res != -1) break; /* Connection established */ >+ } >+ >+ if( addr == NULL ) > { >- error("Socket creation failed for %s!", m_pNetAddress->GetHost() ); >+ error("Socket creation or binding failed for %s!", m_pNetAddress->GetHost() ); > return -1; > } > >- memset(&m_SocketAddress, '\0', sizeof(m_SocketAddress)); >- m_SocketAddress.sin_family = AF_INET; >- m_SocketAddress.sin_addr.s_addr = htonl(INADDR_ANY); >- m_SocketAddress.sin_port = htons( m_pNetAddress->GetPort() ); >- >- if( bind( m_iSocket, (struct sockaddr *) &m_SocketAddress, sizeof(m_SocketAddress)) < 0) >- { >- error( "binding socket failed for %s!", m_pNetAddress->GetHost() ); >- return -1; >- } >+ freeaddrinfo( addr_list ); /* No longer needed */ > > if( listen( m_iSocket, 10 ) < 0 ) > { >diff -Naur nzbget-0.2.3/Connection.h nzbget-0.2.3-ipv6/Connection.h >--- nzbget-0.2.3/Connection.h 2005-09-02 09:00:41.000000000 +0200 >+++ nzbget-0.2.3-ipv6/Connection.h 2008-01-27 14:21:37.000000000 +0100 >@@ -42,7 +42,6 @@ > class Connection > { > protected: >- struct sockaddr_in m_SocketAddress; > NetAddress* m_pNetAddress; > int m_iSocket; > int m_iStatus; ></PRE></BODY></HTML>
Did you submit the upstream? (BTW, 0.3.0 was released last November).
Created attachment 141877 [details, diff] Better patch
Yes, I submitted it upstream and I saw 0.3.0 is out. The patch may also be applicable to 0.3.0, as it uses a similar Connection class. I didn't try 0.3.0.
Created attachment 142397 [details, diff] Better patch Had to remove one more line that wasn't used to make it work.
Created attachment 142402 [details] ebuild that uses the ipv6 patch Added one epatch line to nzbget-0.2.3-r1.ebuild
0.2.3 is no longer in the tree, and such feature requests belong more to the uptsream bug tracker than to a distribution.
See Bug #231740 for a patch for the current version of nzbget.