Index: bitlbee.c
===================================================================
--- bitlbee.c	(revision c511365ddc57359ab3020ccbd3f20e23b55ba5ca)
+++ bitlbee.c	(revision e9b755e3726fa41ac2d4ed1c3a6192d1af68edbc)
@@ -38,9 +38,5 @@
 int bitlbee_daemon_init()
 {
-#ifdef IPV6
-	int use_ipv6 = 1;
-	struct sockaddr_in6 listen_addr6;
-#endif
-	struct sockaddr_in listen_addr;
+	struct addrinfo *res, hints, *addrinfo_bind;
 	int i;
 	FILE *fp;
@@ -49,59 +45,42 @@
 	log_link( LOGLVL_WARNING, LOGOUTPUT_SYSLOG );
 	
-#ifdef IPV6
-	if( ( global.listen_socket = socket( AF_INET6, SOCK_STREAM, 0 ) ) == -1 )
-	{
-		use_ipv6 = 0;
-#endif
-		global.listen_socket = socket( AF_INET, SOCK_STREAM, 0 );
-#ifdef IPV6
-	}
-#endif
-	if( global.listen_socket == -1 )
-	{
-		log_error( "socket" );
-		return( -1 );
-	}
-	
-	/* TIME_WAIT (?) sucks.. */
-	i = 1;
-	setsockopt( global.listen_socket, SOL_SOCKET, SO_REUSEADDR, &i, sizeof( i ) );
-	
-#ifdef IPV6
-	memset( &listen_addr6, 0, sizeof( listen_addr6 ) );
-	listen_addr6.sin6_family = AF_INET6;
-	listen_addr6.sin6_port = htons( global.conf->port );
-	if( ( i = inet_pton( AF_INET6, ipv6_wrap( global.conf->iface ), &listen_addr6.sin6_addr ) ) != 1 )
-	{
-		/* Forget about IPv6 in this function. */
-		use_ipv6 = 0;
-#endif
-		memset( &listen_addr, 0, sizeof( listen_addr ) );
-		listen_addr.sin_family = AF_INET;
-		listen_addr.sin_port = htons( global.conf->port );
-		if( strcmp( global.conf->iface, "::" ) == 0 )
-			i = inet_pton( AF_INET, "0.0.0.0", &listen_addr.sin_addr );
-		else
-			i = inet_pton( AF_INET, global.conf->iface, &listen_addr.sin_addr );
-#ifdef IPV6
-	}
-#endif
-	
-	if( i != 1 )
-	{
-		log_message( LOGLVL_ERROR, "Couldn't parse address `%s'", global.conf->iface );
-		return( -1 );
-	}
-	
-#ifdef IPV6
-	if( !use_ipv6 || ( i = bind( global.listen_socket, (struct sockaddr *) &listen_addr6, sizeof( listen_addr6 ) ) ) == -1 )
-#endif
-		i = bind( global.listen_socket, (struct sockaddr *) &listen_addr, sizeof( listen_addr ) );
-	if( i == -1 )
-	{
-		log_error( "bind" );
-		return( -1 );
-	}
-	
+	memset(&hints, 0, sizeof(hints));
+	hints.ai_family = PF_UNSPEC;
+	hints.ai_socktype = SOCK_STREAM;
+	hints.ai_flags = AI_ADDRCONFIG | AI_PASSIVE;
+
+	i = getaddrinfo(global.conf->iface, global.conf->port, &hints, 
+						&addrinfo_bind);
+	if (i) {
+		log_message( LOGLVL_ERROR, "Couldn't parse address `%s': %s", 
+					 global.conf->iface, gai_strerror(i) );
+		return -1;
+	}
+
+	global.listen_socket = -1;
+
+	for (res = addrinfo_bind; res; res = res->ai_next) {
+		global.listen_socket = socket(res->ai_family, res->ai_socktype, 
+									  res->ai_protocol);
+		if (global.listen_socket < 0)
+			continue;
+
+		/* TIME_WAIT (?) sucks.. */
+		i = 1;
+		setsockopt( global.listen_socket, SOL_SOCKET, SO_REUSEADDR, &i, 
+					sizeof( i ) );
+
+		i = bind( global.listen_socket, res->ai_addr, res->ai_addrlen);
+		if( i == -1 )
+		{
+			log_error( "bind" );
+			return( -1 );
+		}
+
+		break;
+	}
+
+	freeaddrinfo(addrinfo_bind);
+
 	i = listen( global.listen_socket, 10 );
 	if( i == -1 )
Index: conf.c
===================================================================
--- conf.c	(revision c511365ddc57359ab3020ccbd3f20e23b55ba5ca)
+++ conf.c	(revision e9b755e3726fa41ac2d4ed1c3a6192d1af68edbc)
@@ -47,10 +47,6 @@
 	conf = g_new0( conf_t, 1 );
 	
-#ifdef IPV6
-	conf->iface = "::";
-#else
-	conf->iface = "0.0.0.0";
-#endif
-	conf->port = 6667;
+	conf->iface = NULL;
+	conf->port = "6667";
 	conf->nofork = 0;
 	conf->verbose = 0;
@@ -89,10 +85,6 @@
 		else if( opt == 'p' )
 		{
-			if( ( sscanf( optarg, "%d", &i ) != 1 ) || ( i <= 0 ) || ( i > 65535 ) )
-			{
-				fprintf( stderr, "Invalid port number: %s\n", optarg );
-				return( NULL );
-			}
-			conf->port = i;
+			g_free( conf->port );
+			conf->port = g_strdup( optarg );
 		}
 		else if( opt == 'P' )
@@ -204,10 +196,5 @@
 			else if( g_strcasecmp( ini->key, "daemonport" ) == 0 )
 			{
-				if( ( sscanf( ini->value, "%d", &i ) != 1 ) || ( i <= 0 ) || ( i > 65535 ) )
-				{
-					fprintf( stderr, "Invalid port number: %s\n", ini->value );
-					return( 0 );
-				}
-				conf->port = i;
+				conf->port = g_strdup( ini->value );
 			}
 			else if( g_strcasecmp( ini->key, "authmode" ) == 0 )
Index: conf.h
===================================================================
--- conf.h	(revision c511365ddc57359ab3020ccbd3f20e23b55ba5ca)
+++ conf.h	(revision e9b755e3726fa41ac2d4ed1c3a6192d1af68edbc)
@@ -33,5 +33,5 @@
 {
 	char *iface;
-	signed int port;
+	char *port;
 	int nofork;
 	int verbose;
Index: configure
===================================================================
--- configure	(revision c511365ddc57359ab3020ccbd3f20e23b55ba5ca)
+++ configure	(revision e9b755e3726fa41ac2d4ed1c3a6192d1af68edbc)
@@ -30,5 +30,4 @@
 gcov=0
 plugins=1
-ipv6=1
 
 events=glib
@@ -71,6 +70,4 @@
 --gcov=0/1	Disable/enable test coverage reporting	$gcov
 --plugins=0/1	Disable/enable plugins support		$plugins
-
---ipv6=0/1	IPv6 socket support			$ipv6
 
 --events=...	Event handler (glib, libevent)		$events
@@ -134,8 +131,4 @@
 #define CPU "$cpu"
 EOF
-
-if [ "$ipv6" = "1" ]; then
-	echo '#define IPV6' >> config.h
-fi
 
 if [ "$debug" = "1" ]; then
Index: irc.c
===================================================================
--- irc.c	(revision c511365ddc57359ab3020ccbd3f20e23b55ba5ca)
+++ irc.c	(revision e9b755e3726fa41ac2d4ed1c3a6192d1af68edbc)
@@ -45,12 +45,6 @@
 {
 	irc_t *irc;
-	struct hostent *peer;
-	unsigned int i;
-	char buf[128];
-#ifdef IPV6
-	struct sockaddr_in6 sock6[1];
-	unsigned int i6;
-#endif
-	struct sockaddr_in sock[1];
+	struct sockaddr_storage sock;
+	socklen_t socklen = sizeof(sock);
 	
 	irc = g_new0( irc_t, 1 );
@@ -71,52 +65,28 @@
 	irc->channel = g_strdup( ROOT_CHAN );
 	
-	i = sizeof( *sock );
-#ifdef IPV6
-	i6 = sizeof( *sock6 );
-#endif
-	
 	if( global.conf->hostname )
 		irc->myhost = g_strdup( global.conf->hostname );
-#ifdef IPV6
-	else if( getsockname( irc->fd, (struct sockaddr*) sock6, &i6 ) == 0 && sock6->sin6_family == AF_INET6 )
-	{
-		if( ( peer = gethostbyaddr( (char*) &sock6->sin6_addr, sizeof( sock6->sin6_addr ), AF_INET6 ) ) )
-			irc->myhost = g_strdup( peer->h_name );
-		else if( inet_ntop( AF_INET6, &sock6->sin6_addr, buf, sizeof( buf ) - 1 ) != NULL )
-			irc->myhost = g_strdup( ipv6_unwrap( buf ) );
-	}
-#endif
-	else if( getsockname( irc->fd, (struct sockaddr*) sock, &i ) == 0 && sock->sin_family == AF_INET )
-	{
-		if( ( peer = gethostbyaddr( (char*) &sock->sin_addr, sizeof( sock->sin_addr ), AF_INET ) ) )
-			irc->myhost = g_strdup( peer->h_name );
-		else if( inet_ntop( AF_INET, &sock->sin_addr, buf, sizeof( buf ) - 1 ) != NULL )
-			irc->myhost = g_strdup( buf );
-	}
-	
-	i = sizeof( *sock );
-#ifdef IPV6
-	i6 = sizeof( *sock6 );
-	if( getpeername( irc->fd, (struct sockaddr*) sock6, &i6 ) == 0 && sock6->sin6_family == AF_INET6 )
-	{
-		if( ( peer = gethostbyaddr( (char*) &sock6->sin6_addr, sizeof( sock6->sin6_addr ), AF_INET6 ) ) )
-			irc->host = g_strdup( peer->h_name );
-		else if( inet_ntop( AF_INET6, &sock6->sin6_addr, buf, sizeof( buf ) - 1 ) != NULL )
-			irc->host = g_strdup( ipv6_unwrap( buf ) );
-	}
-	else
-#endif
-	if( getpeername( irc->fd, (struct sockaddr*) sock, &i ) == 0 && sock->sin_family == AF_INET )
-	{
-		if( ( peer = gethostbyaddr( (char*) &sock->sin_addr, sizeof( sock->sin_addr ), AF_INET ) ) )
-			irc->host = g_strdup( peer->h_name );
-		else if( inet_ntop( AF_INET, &sock->sin_addr, buf, sizeof( buf ) - 1 ) != NULL )
-			irc->host = g_strdup( buf );
-	}
-	
-	/* Rare, but possible. */
-	if( !irc->host ) irc->host = g_strdup( "localhost." );
-	if( !irc->myhost ) irc->myhost = g_strdup( "localhost." );
-
+	else if( getsockname( irc->fd, (struct sockaddr*) &sock, &socklen ) == 0) 
+	{
+		irc->myhost = g_new0(char, NI_MAXHOST);
+
+		if (getnameinfo((struct sockaddr *)&sock, socklen, irc->myhost, 
+						NI_MAXHOST, NULL, -1, 0)) {
+			/* Rare, but possible. */
+			strncpy(irc->myhost, "localhost.", NI_MAXHOST);
+		}
+	}
+	
+	if( getpeername( irc->fd, (struct sockaddr*) &sock, &socklen ) == 0)
+	{
+		irc->host = g_new0(char, NI_MAXHOST);
+
+		if (getnameinfo((struct sockaddr *)&sock, socklen, irc->host, 
+						NI_MAXHOST, NULL, -1, 0)) {
+			/* Rare, but possible. */
+			strncpy(irc->myhost, "localhost.", NI_MAXHOST);
+		}
+	}
+	
 	if( global.conf->ping_interval > 0 && global.conf->ping_timeout > 0 )
 		irc->ping_source_id = b_timeout_add( global.conf->ping_interval * 1000, irc_userping, irc );
Index: lib/misc.c
===================================================================
--- lib/misc.c	(revision c511365ddc57359ab3020ccbd3f20e23b55ba5ca)
+++ lib/misc.c	(revision e9b755e3726fa41ac2d4ed1c3a6192d1af68edbc)
@@ -322,44 +322,4 @@
 }
 
-#ifdef IPV6
-/* Wrap an IPv4 address into IPv6 space. Not thread-safe... */
-char *ipv6_wrap( char *src )
-{
-	static char dst[64];
-	int i;
-	
-	for( i = 0; src[i]; i ++ )
-		if( ( src[i] < '0' || src[i] > '9' ) && src[i] != '.' )
-			break;
-	
-	/* Hmm, it's not even an IP... */
-	if( src[i] )
-		return src;
-	
-	g_snprintf( dst, sizeof( dst ), "::ffff:%s", src );
-	
-	return dst;
-}
-
-/* Unwrap an IPv4 address into IPv6 space. Thread-safe, because it's very simple. :-) */
-char *ipv6_unwrap( char *src )
-{
-	int i;
-	
-	if( g_strncasecmp( src, "::ffff:", 7 ) != 0 )
-		return src;
-	
-	for( i = 7; src[i]; i ++ )
-		if( ( src[i] < '0' || src[i] > '9' ) && src[i] != '.' )
-			break;
-	
-	/* Hmm, it's not even an IP... */
-	if( src[i] )
-		return src;
-	
-	return ( src + 7 );
-}
-#endif
-
 /* Convert from one charset to another.
    
Index: lib/misc.h
===================================================================
--- lib/misc.h	(revision c511365ddc57359ab3020ccbd3f20e23b55ba5ca)
+++ lib/misc.h	(revision e9b755e3726fa41ac2d4ed1c3a6192d1af68edbc)
@@ -52,7 +52,4 @@
 G_MODULE_EXPORT void http_encode( char *s );
 
-G_MODULE_EXPORT char *ipv6_wrap( char *src );
-G_MODULE_EXPORT char *ipv6_unwrap( char *src );
-
 G_MODULE_EXPORT signed int do_iconv( char *from_cs, char *to_cs, char *src, char *dst, size_t size, size_t maxbuf );
 
