]> git.ipfire.org Git - thirdparty/squid.git/blobdiff - src/FwdState.h
Source Format Enforcement (#532)
[thirdparty/squid.git] / src / FwdState.h
index d19aea6d8a45b1cf992894a84dbdc26814a3b024..ae1434d08b8cd046eb28404fd77cbf1f293b480c 100644 (file)
@@ -1,13 +1,27 @@
+/*
+ * Copyright (C) 1996-2020 The Squid Software Foundation and contributors
+ *
+ * Squid software is distributed under GPLv2+ license and includes
+ * contributions from numerous individuals and organizations.
+ * Please see the COPYING and CONTRIBUTORS files for details.
+ */
+
 #ifndef SQUID_FORWARD_H
 #define SQUID_FORWARD_H
 
+#include "base/CbcPointer.h"
+#include "base/forward.h"
 #include "base/RefCount.h"
+#include "clients/forward.h"
 #include "comm.h"
 #include "comm/Connection.h"
+#include "comm/ConnOpener.h"
 #include "err_type.h"
 #include "fde.h"
 #include "http/StatusCode.h"
 #include "ip/Address.h"
+#include "PeerSelectState.h"
+#include "security/forward.h"
 #if USE_OPENSSL
 #include "ssl/support.h"
 #endif
@@ -18,6 +32,13 @@ class AccessLogEntry;
 typedef RefCount<AccessLogEntry> AccessLogEntryPointer;
 class ErrorState;
 class HttpRequest;
+class PconnPool;
+class ResolvedPeers;
+typedef RefCount<ResolvedPeers> ResolvedPeersPointer;
+
+class HappyConnOpener;
+typedef CbcPointer<HappyConnOpener> HappyConnOpenerPointer;
+class HappyConnOpenerAnswer;
 
 #if USE_OPENSSL
 namespace Ssl
@@ -27,36 +48,39 @@ class CertValidationResponse;
 };
 #endif
 
-/**
- * Returns the TOS value that we should be setting on the connection
- * to the server, based on the ACL.
- */
-tos_t GetTosToServer(HttpRequest * request);
+/// Sets initial TOS value and Netfilter for the future outgoing connection.
+/// Updates the given Connection object, not the future transport connection.
+void GetMarkingsToServer(HttpRequest * request, Comm::Connection &conn);
 
-/**
- * Returns the Netfilter mark value that we should be setting on the
- * connection to the server, based on the ACL.
- */
-nfmark_t GetNfmarkToServer(HttpRequest * request);
+/// Recomputes and applies TOS value and Netfilter to the outgoing connection.
+/// Updates both the given Connection object and the transport connection.
+void ResetMarkingsToServer(HttpRequest *, Comm::Connection &);
 
 class HelperReply;
 
-class FwdState : public RefCountable
+class FwdState: public RefCountable, public PeerSelectionInitiator
 {
+    CBDATA_CHILD(FwdState);
+
 public:
     typedef RefCount<FwdState> Pointer;
-    ~FwdState();
+    virtual ~FwdState();
     static void initModule();
 
     /// Initiates request forwarding to a peer or origin server.
     static void Start(const Comm::ConnectionPointer &client, StoreEntry *, HttpRequest *, const AccessLogEntryPointer &alp);
     /// Same as Start() but no master xaction info (AccessLogEntry) available.
     static void fwdStart(const Comm::ConnectionPointer &client, StoreEntry *, HttpRequest *);
+    /// time left to finish the whole forwarding process (which started at fwdStart)
+    static time_t ForwardTimeout(const time_t fwdStart);
+    /// Whether there is still time to re-try after a previous connection failure.
+    /// \param fwdStart The start time of the peer selection/connection process.
+    static bool EnoughTimeToReForward(const time_t fwdStart);
 
     /// This is the real beginning of server connection. Call it whenever
     /// the forwarding server destination has changed and a new one needs to be opened.
     /// Produces the cannot-forward error on fail if no better error exists.
-    void startConnectionOrFail();
+    void useDestinations();
 
     void fail(ErrorState *err);
     void unregister(Comm::ConnectionPointer &conn);
@@ -67,13 +91,11 @@ public:
     bool reforwardableStatus(const Http::StatusCode s) const;
     void serverClosed(int fd);
     void connectStart();
-    void connectDone(const Comm::ConnectionPointer & conn, comm_err_t status, int xerrno);
-    void connectTimeout(int fd);
-    void initiateSSL();
-    void negotiateSSL(int fd);
+    void connectDone(const Comm::ConnectionPointer & conn, Comm::Flag status, int xerrno);
     bool checkRetry();
     bool checkRetriable();
     void dispatch();
+
     void pconnPush(Comm::ConnectionPointer & conn, const char *domain);
 
     bool dontRetry() { return flags.dont_retry; }
@@ -83,18 +105,17 @@ public:
     /** return a ConnectionPointer to the current server connection (may or may not be open) */
     Comm::ConnectionPointer const & serverConnection() const { return serverConn; };
 
-#if USE_OPENSSL
-    /// Callback function called when squid receive message from cert validator helper
-    static void sslCrtvdHandleReplyWrapper(void *data, Ssl::CertValidationResponse const &);
-    /// Process response from cert validator helper
-    void sslCrtvdHandleReply(Ssl::CertValidationResponse const &);
-    /// Check SSL errors returned from cert validator against sslproxy_cert_error access list
-    Ssl::CertErrors *sslCrtvdCheckForErrors(Ssl::CertValidationResponse const &, Ssl::ErrorDetail *&);
-#endif
 private:
     // hidden for safer management of self; use static fwdStart
     FwdState(const Comm::ConnectionPointer &client, StoreEntry *, HttpRequest *, const AccessLogEntryPointer &alp);
     void start(Pointer aSelf);
+    void stopAndDestroy(const char *reason);
+
+    /* PeerSelectionInitiator API */
+    virtual void noteDestination(Comm::ConnectionPointer conn) override;
+    virtual void noteDestinationsEnd(ErrorState *selectionError) override;
+
+    void noteConnection(HappyConnOpenerAnswer &);
 
 #if STRICT_ORIGINAL_DST
     void selectPeerForIntercepted();
@@ -103,9 +124,42 @@ private:
     void doneWithRetries();
     void completed();
     void retryOrBail();
+
+    void usePinned();
+
+    /// whether a pinned to-peer connection can be replaced with another one
+    /// (in order to retry or reforward a failed request)
+    bool pinnedCanRetry() const;
+
     ErrorState *makeConnectingError(const err_type type) const;
+    void connectedToPeer(Security::EncryptorAnswer &answer);
     static void RegisterWithCacheManager(void);
 
+    void establishTunnelThruProxy();
+    void tunnelEstablishmentDone(Http::TunnelerAnswer &answer);
+    void secureConnectionToPeerIfNeeded();
+    void successfullyConnectedToPeer();
+
+    /// stops monitoring server connection for closure and updates pconn stats
+    void closeServerConnection(const char *reason);
+
+    void syncWithServerConn(const Comm::ConnectionPointer &server, const char *host, const bool reused);
+    void syncHierNote(const Comm::ConnectionPointer &server, const char *host);
+
+    /// whether we have used up all permitted forwarding attempts
+    bool exhaustedTries() const;
+
+    /// \returns the time left for this connection to become connected or 1 second if it is less than one second left
+    time_t connectingTimeout(const Comm::ConnectionPointer &conn) const;
+
+    /// whether we are waiting for HappyConnOpener
+    /// same as calls.connector but may differ from connOpener.valid()
+    bool opening() const { return connOpener.set(); }
+
+    void cancelOpening(const char *reason);
+
+    void notifyConnOpener();
+
 public:
     StoreEntry *entry;
     HttpRequest *request;
@@ -118,7 +172,7 @@ private:
     ErrorState *err;
     Comm::ConnectionPointer clientConn;        ///< a possibly open connection to the client.
     time_t start_t;
-    int n_tries;
+    int n_tries; ///< the number of forwarding attempts so far
 
     // AsyncCalls which we set and may need cancelling.
     struct {
@@ -129,21 +183,24 @@ private:
         bool connected_okay; ///< TCP link ever opened properly. This affects retry of POST,PUT,CONNECT,etc
         bool dont_retry;
         bool forward_completed;
+        bool destinationsFound; ///< at least one candidate path found
     } flags;
 
-    /** connections to open, in order, until successful */
-    Comm::ConnectionList serverDestinations;
-
+    HappyConnOpenerPointer connOpener; ///< current connection opening job
+    ResolvedPeersPointer destinations; ///< paths for forwarding the request
     Comm::ConnectionPointer serverConn; ///< a successfully opened connection to a server.
 
+    AsyncCall::Pointer closeHandler; ///< The serverConn close handler
+
     /// possible pconn race states
     typedef enum { raceImpossible, racePossible, raceHappened } PconnRace;
     PconnRace pconnRace; ///< current pconn race state
-
-    // NP: keep this last. It plays with private/public
-    CBDATA_CLASS2(FwdState);
 };
 
 void getOutgoingAddress(HttpRequest * request, Comm::ConnectionPointer conn);
 
+/// a collection of previously used persistent Squid-to-peer HTTP(S) connections
+extern PconnPool *fwdPconnPool;
+
 #endif /* SQUID_FORWARD_H */
+