--------------------- PatchSet 4664 Date: 2007/05/29 08:58:16 Author: amosjeffries Branch: squid3-ipv6 Tag: (none) Log: Fix: squid.conf parse dying on ACL /w IPv6 & netmask. Members: src/ACLIP.cc:1.8.2.27->1.8.2.28 Index: squid3/src/ACLIP.cc =================================================================== RCS file: /cvsroot/squid-sf//squid3/src/ACLIP.cc,v retrieving revision 1.8.2.27 retrieving revision 1.8.2.28 diff -u -r1.8.2.27 -r1.8.2.28 --- squid3/src/ACLIP.cc 29 May 2007 00:09:49 -0000 1.8.2.27 +++ squid3/src/ACLIP.cc 29 May 2007 08:58:16 -0000 1.8.2.28 @@ -1,5 +1,5 @@ /* - * $Id: ACLIP.cc,v 1.8.2.27 2007/05/29 00:09:49 amosjeffries Exp $ + * $Id: ACLIP.cc,v 1.8.2.28 2007/05/29 08:58:16 amosjeffries Exp $ * * DEBUG: section 28 Access Control * AUTHOR: Duane Wessels @@ -238,7 +238,7 @@ LOCAL_ARRAY(char, l_mask, 256); acl_ip_data *r; acl_ip_data **Q; - char **x; + IPAddress temp; char c; debugs(28, 5, "aclParseIpData: " << t); acl_ip_data *q = new acl_ip_data; @@ -291,41 +291,43 @@ * ipcache hasn't been initialized */ - struct hostent *hp; + debugs(28, 5, "aclParseIpData: Lookup Host/IP " << l_addr1); + struct addrinfo *hp = NULL, *x = NULL, *y = NULL; + IPAddress *prev_addr = NULL; - if ((hp = gethostbyname(l_addr1)) == NULL) { + getaddrinfo(l_addr1,NULL,NULL,&hp); + if (hp == NULL) { debugs(28, 0, "aclParseIpData: Bad host/IP: '" << t << "'"); self_destruct(); } Q = &q; - for (x = hp->h_addr_list; x != NULL && *x != NULL; x++) { + for (x = hp; x != NULL;) { if ((r = *Q) == NULL) r = *Q = new acl_ip_data; - switch(hp->h_addrtype) - { - case AF_INET: - { - r->addr1 = *( (struct in_addr*)*x ); - debugs(28, 3, "aclParseIpData: Located host/IP: '" << r->addr1 << "'"); - } break; - - case AF_INET6: - { -#if USE_IPV6 - r->addr1 = *( (struct in6_addr*)*x ); - debugs(28, 3, "aclParseIpData: Located host/IP: '" << r->addr1 << "'"); -#else - debugs(28, 1, "WARNING: aclParseIpData: Dropping IPv6 host/IP: '" << l_addr1 << "'"); -#endif - } break; - - default: - debugs(28, 1, "WARNING: aclParseIpData: Defaulting host/IP: '" << l_addr1 << "' to ANY."); - r->addr1.SetAnyAddr(); + /* addrinfo operator in IPA will skip non-accepted results silently */ + /* to get all results tested, we must pull them individually and unlinked.*/ + y = x; + x = x->ai_next; + y->ai_next = NULL; + r->addr1 = *y; + freeaddrinfo(y); + + /* getaddrinfo given a host has a nasty tendency to return duplicate addr's */ + /* BUT sorted fortunately, so we can drop most of them easily */ + if( prev_addr && r->addr1 == *prev_addr) { + debugs(28, 3, "aclParseIpData: Duplicate host/IP: '" << r->addr1 << "' dropped."); + delete r; + *Q = NULL; + continue; } + else + prev_addr = &r->addr1; + + if( !r->addr1.IsAnyAddr() ) + debugs(28, 3, "aclParseIpData: Located host/IP: '" << r->addr1 << "'"); r->addr2.SetAnyAddr();