This patch backs out part of the patch for Bug #2222 and replaces it by
crudely cycling over the available addresses, trying to skip over
addresses not compatible with the current socket.

This solves issues seen when using tproxy or tcp_outgoing_address and
DNS of the requested host returns AAAA records in addition to A records.

This change is interim, waiting for the larger connection setup
overhaul. But seems to do the trick at least for me in tproxy & ipv4
setups. Unfortunately I do not have an IPv6 connection at the moment to
test IPv6 on, but I don't see how it could break IPv6.

One effect of this change is that there will be no fallback to the other
IP generation if the socket is configured to a specific outgoing
address. Priorly the code threw away the outgoing address and tried
again when encountering an incompatibility.

Regards
Henrik
# Bazaar merge directive format 2 (Bazaar 0.90)
# revision_id: hen...@henriknordstrom.net-20100511013541-\
#   1v1dnocxttvwqv82
# target_branch: http://squid-cache.org/bzr/squid3/branches/SQUID_3_1/
# testament_sha1: 261b470e0c4b4451cc5e5541e62463f5d59456dd
# timestamp: 2010-05-11 03:35:58 +0200
# base_revision_id: squ...@treenet.co.nz-20100505074245-\
#   qpjwdvcumn8f94bd
# 
# Begin patch
=== modified file 'src/comm.cc'
--- src/comm.cc	2010-04-23 01:17:20 +0000
+++ src/comm.cc	2010-05-11 01:35:41 +0000
@@ -968,9 +968,6 @@
 int
 ConnectStateData::commResetFD()
 {
-    struct addrinfo *AI = NULL;
-    IpAddress nul;
-    int new_family = AF_UNSPEC;
 
 // XXX: do we have to check this?
 //
@@ -979,21 +976,19 @@
 
     statCounter.syscalls.sock.sockets++;
 
-    /* setup a bare-bones addrinfo */
-    /* TODO INET6: for WinXP we may need to check the local_addr type and setup the family properly. */
-    nul.GetAddrInfo(AI);
-    new_family = AI->ai_family;
+    fde *F = &fd_table[fd];
 
+    struct addrinfo *AI = NULL;
+    F->local_addr.GetAddrInfo(AI);
     int fd2 = socket(AI->ai_family, AI->ai_socktype, AI->ai_protocol);
 
-    nul.FreeAddrInfo(AI);
-
     if (fd2 < 0) {
         debugs(5, DBG_CRITICAL, HERE << "WARNING: FD " << fd2 << " socket failed to allocate: " << xstrerror());
 
         if (ENFILE == errno || EMFILE == errno)
             fdAdjustReserved();
 
+        F->local_addr.FreeAddrInfo(AI);
         return 0;
     }
 
@@ -1013,17 +1008,15 @@
 
         close(fd2);
 
+        F->local_addr.FreeAddrInfo(AI);
         return 0;
     }
     commResetSelect(fd);
 
     close(fd2);
-    fde *F = &fd_table[fd];
-
-    /* INET6: copy the new sockets family type to the FDE table */
-    fd_table[fd].sock_family = new_family;
-
-    fd_table[fd].flags.called_connect = 0;
+
+    F->flags.called_connect = 0;
+
     /*
      * yuck, this has assumptions about comm_open() arguments for
      * the original socket
@@ -1034,9 +1027,6 @@
         comm_set_transparent(fd);
     }
 
-    AI = NULL;
-    F->local_addr.GetAddrInfo(AI);
-
     if (commBind(fd, *AI) != COMM_OK) {
         debugs(5, DBG_CRITICAL, "WARNING: Reset of FD " << fd << " for " << F->local_addr << " failed to bind: " << xstrerror());
         F->local_addr.FreeAddrInfo(AI);
@@ -1104,8 +1094,7 @@
 void
 ConnectStateData::connect()
 {
-    if (S.IsAnyAddr())
-        defaults();
+    defaults();
 
     debugs(5,5, HERE << "to " << S);
 
@@ -1125,10 +1114,18 @@
 #if USE_IPV6
     case COMM_ERR_PROTOCOL:
         /* problem using the desired protocol over this socket.
-         * count the connection attempt, reset the socket, and immediately try again */
+         * skip to the next address and hope it's more compatible
+         * but do not mark the current address as bad
+         */
         tries++;
-        commResetFD();
-        connect();
+        if (commRetryConnect()) {
+            /* Force an addr cycle to move forward to the next possible address */
+            ipcacheCycleAddr(host, NULL);
+            eventAdd("commReconnect", commReconnect, this, this->addrcount == 1 ? 0.05 : 0.0, 0);
+        } else {
+            debugs(5, 5, HERE << "FD " << fd << ": * - ERR tried too many times already.");
+            callCallback(COMM_ERR_CONNECT, errno);
+        }
         break;
 #endif
 
@@ -1232,7 +1229,6 @@
 
     debugs(5, 9, "comm_connect_addr: connecting socket " << sock << " to " << address << " (want family: " << F->sock_family << ")");
 
-    /* BUG 2222 FIX: reset the FD when its found to be IPv4 in IPv6 mode */
     /* inverse case of IPv4 failing to connect on IPv6 socket is handeld post-connect.
      * this case must presently be handled here since the GetAddrInfo asserts on bad mappings.
      * eventually we want it to throw a Must() that gets handled there instead of this if.

# Begin bundle
IyBCYXphYXIgcmV2aXNpb24gYnVuZGxlIHY0CiMKQlpoOTFBWSZTWX4OKCkAAmzfgEZQUff////n
lgq////6UAU4q9N3VLgLrBXOQJIkNEGjTKaYBU/1Gkwp+ST9Q9NE0ZQPU2gmgSUCYTUybUT1T1PU
fqRtQAA0ANAAAAlNIJoKbJTymzVDyJjUNHpNABoA0NNA9Q4yZNGIYmmAgYE0wRgmJppoAMIJJEwK
YU/U1T9TUGjahoGgYmg0yAAAJDB28+jHXGxZ90YN00xKUliRRGB0T6N0UrrWoJrFvaNcIhqQWu5k
TD8F/DZbNWRd6q8wzDTGDl4zk6fhZ3vzjjx8J8cEwJMbKcv3yfUbfOuu+UdEdKhi6Sm4ljN4Ga5n
Ymkwbbks5M1F1wZn5t9nuq4NT25MJZ6Y8060OyjJHqeR11eGfFKzD/QzCgu7XkecpEIWxmm4r4wL
Ki4pErvuPp51Ut2Ryx69sNXT0ENk7PwvZxXJbccJEcGQ8zNS2cyKMOo2Ouu1mJX9Pon5fMnKGZlL
3u3I7q4Bf4IC4dGJd4I351rpVshI0uRT+1XgZLkDYd2I1c1+3pRf7e0nSHY5GCptl100RDCGrYDc
mRNsUXWNMKYoILsI3jYO4ruouOeA0kFiVlUIjXJ7hhRGTe9M61xyCcA17Tg0ftxY6yiLCh9iCpBt
dXHAfDwp8SwfwWmBEWRUZGweIuVhlqWOBonJ/AXOYlN9FoVVwX0ZdneThFUrUo1icUueDxRTGFNk
yoVNURwyuFJpOTyE05xcs9Ci31fhnR9KW2D+GdygC5Yt+lJZjEtuzM1j12OkoZYcWUg3jipXKO5W
LxhfRbdg2+ZUhFEMyi3EVKFRsWFpwG7xrEmPvGyZSOg8sVNqxiYsYXhOQ2vdKqZcENwJpgmMqLMt
ikkiWWK6oVlxKWG49WNzB0mxdXeQalMjwYc3t8JSrMdLuatLBHHvLaYRciz9SJI9iWkNvUsE4zLE
wxxk+r9ePDHf3Uf56YbtPl5jVy+5M/9BoVp6nr60vOvoVcqbiiExyWy0ZV9pJbVpcNkOb5apiMA3
m0/Y75uF3iY7V0OnaBhKDAaAruL4tkaiwpe5O+Xw/NQoSMnn8PjQOUx5/Hv4jGUvVmCN2jakq8TF
0xnvPEs+a+e0Ki5+fgZa6xm6CcMVnFhzj3Oc+Qp/R8DLyU1Ymp11TUNs669MBwzEVImeicm5Owan
MmTCfUqe0uOtyu3jrmQrUErAa+6qbJLCe2G/y3RIwqdNcjbo2985irE0parokge+Frc5aFt6ETwM
iWzAPTqEoaMyZEbZdKmgZ4ligPUbJDfeXRMBKXFGfDqOXIYyo0KbMYvx9tekvnlzx99aHDe90Vns
e9CozA6ePptNqb8Jbol/dhEQ2anvvVUjciEp8tBBJZFIrxr8wvzbsGaSOChkp+eo6gJt3RHb1q3V
UxwUEuUIukyjasb4yWdmd+MkwZudP7NksuepMlrTosMSkoL1uhyMqChTkYbCaDQdiZMKUkkGCFoc
iWQRIH1TYyDHtC30pTSWLCmyGV+oNhXbViCpyBYnFTvYCRIuoPa5laiXXa4YpA/fxvJZMC4MuTZw
tXklV/OyfdgaaaKFzCSP6sJUnMZjouCOIW/o1aGiYmhwua6DUGm8oGedwohh18tbE7CU9ySlPea2
TBPMxmraaJOyWEEU/suDSKU4iTlM2MhFxKgD5aNyT8SFQbIKAZQOZ8NWfcny1xrir3wUBi1m0KNZ
ItKzrNJaquRqv4hyawJhem94GNcg1UcRYp1FUTyzOhxo5MNi144ubF/iFIXKuWqhbJMAxFj/lXm8
ArkYinGWyl7/SoNI9u4Jbcy/A8Z/xdyRThQkH4OKCkA=

Reply via email to