]> git.ipfire.org Git - thirdparty/squid.git/blobdiff - src/FwdState.cc
Merged from trunk (r13356).
[thirdparty/squid.git] / src / FwdState.cc
index 6847fed133923852177ff5c66f2836dc691baf19..cb0befaaa0dfd3b565a8dce6ab2f66122520cb73 100644 (file)
@@ -48,6 +48,7 @@
 #include "fd.h"
 #include "fde.h"
 #include "ftp.h"
+#include "FtpGatewayServer.h"
 #include "FwdState.h"
 #include "globals.h"
 #include "gopher.h"
@@ -71,7 +72,7 @@
 #include "StoreClient.h"
 #include "urn.h"
 #include "whois.h"
-#if USE_SSL
+#if USE_OPENSSL
 #include "ssl/cert_validate_message.h"
 #include "ssl/Config.h"
 #include "ssl/ErrorDetail.h"
@@ -85,7 +86,7 @@
 
 static PSC fwdPeerSelectionCompleteWrapper;
 static CLCB fwdServerClosedWrapper;
-#if USE_SSL
+#if USE_OPENSSL
 static PF fwdNegotiateSSLWrapper;
 #endif
 static CNCB fwdConnectDoneWrapper;
@@ -112,7 +113,7 @@ FwdState::abort(void* d)
     } else {
         debugs(17, 7, HERE << "store entry aborted; no connection to close");
     }
-    fwd->serverDestinations.clean();
+    fwd->serverDestinations.clear();
     fwd->self = NULL;
 }
 
@@ -229,7 +230,7 @@ FwdState::completed()
             assert(err);
             errorAppendEntry(entry, err);
             err = NULL;
-#if USE_SSL
+#if USE_OPENSSL
             if (request->flags.sslPeek && request->clientConnectionManager.valid()) {
                 CallJobHere1(17, 4, request->clientConnectionManager, ConnStateData,
                              ConnStateData::httpsPeeked, Comm::ConnectionPointer(NULL));
@@ -277,7 +278,7 @@ FwdState::~FwdState()
         serverConn->close();
     }
 
-    serverDestinations.clean();
+    serverDestinations.clear();
 
     debugs(17, 3, HERE << "FwdState destructor done");
 }
@@ -472,7 +473,7 @@ FwdState::complete()
         entry->reset();
 
         // drop the last path off the selection list. try the next one.
-        serverDestinations.shift();
+        serverDestinations.erase(serverDestinations.begin());
         startConnectionOrFail();
 
     } else {
@@ -508,7 +509,7 @@ fwdServerClosedWrapper(const CommCloseCbParams &params)
     fwd->serverClosed(params.fd);
 }
 
-#if USE_SSL
+#if USE_OPENSSL
 static void
 fwdNegotiateSSLWrapper(int fd, void *data)
 {
@@ -611,7 +612,7 @@ FwdState::retryOrBail()
         if (pconnRace == raceHappened)
             debugs(17, 4, HERE << "retrying the same destination");
         else
-            serverDestinations.shift(); // last one failed. try another.
+            serverDestinations.erase(serverDestinations.begin()); // last one failed. try another.
         startConnectionOrFail();
         return;
     }
@@ -646,7 +647,7 @@ FwdState::handleUnregisteredServerEnd()
     retryOrBail();
 }
 
-#if USE_SSL
+#if USE_OPENSSL
 void
 FwdState::negotiateSSL(int fd)
 {
@@ -1032,7 +1033,7 @@ FwdState::connectDone(const Comm::ConnectionPointer &conn, comm_err_t status, in
     if (serverConnection()->getPeer())
         peerConnectSucceded(serverConnection()->getPeer());
 
-#if USE_SSL
+#if USE_OPENSSL
     if (!request->flags.pinned) {
         if ((serverConnection()->getPeer() && serverConnection()->getPeer()->use_ssl) ||
                 (!serverConnection()->getPeer() && request->protocol == AnyP::PROTO_HTTPS) ||
@@ -1043,6 +1044,16 @@ FwdState::connectDone(const Comm::ConnectionPointer &conn, comm_err_t status, in
     }
 #endif
 
+    const CbcPointer<ConnStateData> &clientConnState =
+        request->clientConnectionManager;
+    if (clientConnState.valid() && clientConnState->isFtp) {
+        // this is not an idle connection, so we do not want I/O monitoring
+        const bool monitor = false;
+        clientConnState->pinConnection(serverConnection(), request,
+                                       serverConnection()->getPeer(), false,
+                                       monitor);
+    }
+
     dispatch();
 }
 
@@ -1054,7 +1065,7 @@ FwdState::connectTimeout(int fd)
     assert(fd == serverDestinations[0]->fd);
 
     if (entry->isEmpty()) {
-        ErrorState *anErr = new ErrorState(ERR_CONNECT_FAIL, Http::scGateway_Timeout, request);
+        ErrorState *anErr = new ErrorState(ERR_CONNECT_FAIL, Http::scGatewayTimeout, request);
         anErr->xerrno = ETIMEDOUT;
         fail(anErr);
 
@@ -1116,13 +1127,14 @@ FwdState::connectStart()
         debugs(17,7, "pinned peer connection: " << pinned_connection);
         // pinned_connection may become nil after a pconn race
         if (pinned_connection)
-            serverConn = pinned_connection->validatePinnedConnection(request, serverDestinations[0]->getPeer());
+            serverConn = pinned_connection->borrowPinnedConnection(request, serverDestinations[0]->getPeer());
         else
             serverConn = NULL;
         if (Comm::IsConnOpen(serverConn)) {
             pinned_connection->stopPinnedConnectionMonitoring();
             flags.connected_okay = true;
             ++n_tries;
+            request->hier.note(serverConn, request->GetHost());
             request->flags.pinned = true;
             request->hier.note(serverConn, pinned_connection->pinning.host);
             if (pinned_connection->pinnedAuth())
@@ -1191,18 +1203,7 @@ FwdState::connectStart()
     entry->mem_obj->checkUrlChecksum();
 #endif
 
-    /* Get the server side TOS and Netfilter mark to be set on the connection. */
-    if (Ip::Qos::TheConfig.isAclTosActive()) {
-        serverDestinations[0]->tos = GetTosToServer(request);
-    }
-#if SO_MARK && USE_LIBCAP
-    serverDestinations[0]->nfmark = GetNfmarkToServer(request);
-    debugs(17, 3, "fwdConnectStart: got outgoing addr " << serverDestinations[0]->local << ", tos " << int(serverDestinations[0]->tos)
-           << ", netfilter mark " << serverDestinations[0]->nfmark);
-#else
-    serverDestinations[0]->nfmark = 0;
-    debugs(17, 3, "fwdConnectStart: got outgoing addr " << serverDestinations[0]->local << ", tos " << int(serverDestinations[0]->tos));
-#endif
+    GetMarkingsToServer(request, *serverDestinations[0]);
 
     calls.connector = commCbCall(17,3, "fwdConnectDoneWrapper", CommConnectCbPtrFun(fwdConnectDoneWrapper, this));
     Comm::ConnOpener *cs = new Comm::ConnOpener(serverDestinations[0], calls.connector, ctimeout);
@@ -1258,7 +1259,7 @@ FwdState::dispatch()
     }
 #endif
 
-#if USE_SSL
+#if USE_OPENSSL
     if (request->flags.sslPeek) {
         CallJobHere1(17, 4, request->clientConnectionManager, ConnStateData,
                      ConnStateData::httpsPeeked, serverConnection());
@@ -1279,7 +1280,7 @@ FwdState::dispatch()
         request->peer_domain = NULL;
 
         switch (request->protocol) {
-#if USE_SSL
+#if USE_OPENSSL
 
         case AnyP::PROTO_HTTPS:
             httpStart(this);
@@ -1295,7 +1296,10 @@ FwdState::dispatch()
             break;
 
         case AnyP::PROTO_FTP:
-            ftpStart(this);
+            if (request->clientConnectionManager->isFtp)
+                ftpGatewayServerStart(this);
+            else
+                ftpStart(this);
             break;
 
         case AnyP::PROTO_CACHE_OBJECT:
@@ -1385,7 +1389,7 @@ ErrorState *
 FwdState::makeConnectingError(const err_type type) const
 {
     return new ErrorState(type, request->flags.needValidation ?
-                          Http::scGateway_Timeout : Http::scServiceUnavailable, request);
+                          Http::scGatewayTimeout : Http::scServiceUnavailable, request);
 }
 
 static void
@@ -1424,7 +1428,7 @@ FwdState::reforwardableStatus(const Http::StatusCode s) const
 
     case Http::scBadGateway:
 
-    case Http::scGateway_Timeout:
+    case Http::scGatewayTimeout:
         return true;
 
     case Http::scForbidden:
@@ -1584,3 +1588,20 @@ GetNfmarkToServer(HttpRequest * request)
     ACLFilledChecklist ch(NULL, request, NULL);
     return aclMapNfmark(Ip::Qos::TheConfig.nfmarkToServer, &ch);
 }
+
+void
+GetMarkingsToServer(HttpRequest * request, Comm::Connection &conn)
+{
+    // Get the server side TOS and Netfilter mark to be set on the connection.
+    if (Ip::Qos::TheConfig.isAclTosActive()) {
+        conn.tos = GetTosToServer(request);
+        debugs(17, 3, "from " << conn.local << " tos " << int(conn.tos));
+    }
+
+#if SO_MARK && USE_LIBCAP
+    conn.nfmark = GetNfmarkToServer(request);
+    debugs(17, 3, "from " << conn.local << " netfilter mark " << conn.nfmark);
+#else
+    conn.nfmark = 0;
+#endif
+}