]> git.ipfire.org Git - thirdparty/squid.git/commitdiff
Allow for custom keywords in ACL lists (in addition to allow/deny).
authorAlex Rousskov <rousskov@measurement-factory.com>
Fri, 4 May 2012 22:17:15 +0000 (16:17 -0600)
committerAlex Rousskov <rousskov@measurement-factory.com>
Fri, 4 May 2012 22:17:15 +0000 (16:17 -0600)
Motivation: Ssl_bump used allow/deny keywords and standard ACL processing. We
wanted to change those keywords to specify how the connection should be bumped
(client-first, server-first, or not bumped at all).

We could implement that using a set of independent ACL lists, each with its
own keyword, similar to how request_header_access and many other options do
it. However, that would mean losing support for slow ACLs (or implementing
such support by hand).  All current request_header_access-like options do not
support slow ACLs because generic ACL code does not preserve information about
which acl_access list has [slowly] matched and, hence, we cannot tell which
custom keyword (e.g., which header name) to use after the match.

To solve the problem, we converted allow_t enum into a class that can carry
the old matching result code (ACCESS_*) and a custom "match kind or keyword"
integer that the caller can optionally inspect if access is allowed (i.e., if
some acl_access list matched).  When a squid.conf option is parsed into an
acl_access object, Squid sets the allow.kind field to the corresponding
keyword. When the ACL list is checked at runtime and there is a match, the
previously set allow.kind value is propagated to the final answer (XXX: not
implemented?) which the high-level caller can optionally check.

The old allow_t-using code does not need to be modified because the new
allow_t class allows for implicit conversion from and to ALLOW_* constants.

Caveat: When no ACLs match, the generic ACL code processing a chain of
acl_access rules will negate the last rule allow/deny keyword. Such "implicit"
rule would not carry any "matched keyword or kind" information (the _implicit_
last ACL list cannot have any explicit keywords). Thus, the high-level caller
should be careful when interpreting the answer to deal with such implicit
matches. Most likely, the high-level code must disclaim support for implicit
rules (in documentation) and treat any matches without keyword information as
if no rule has matched.

Eventually, the core ACL code can be reshaped so that the caller can control
whether implicit rules are allowed.

src/acl/Acl.h

index 66b142457015bdd8d86d64b88165f6e6bf255d5a..359b302a525a735c03478942d4ae244523f7da05 100644 (file)
@@ -118,7 +118,33 @@ typedef enum {
     ACCESS_AUTH_REQUIRED,    // Missing Credentials
     ACCESS_AUTH_EXPIRED_OK,  // Expired now. Were Okay.
     ACCESS_AUTH_EXPIRED_BAD  // Expired now. Were Failed.
-} allow_t;
+} aclMatchCode;
+
+/// \ingroup ACLAPI
+/// ACL check answer; TODO: Rename to Acl::Answer
+class allow_t {
+public:
+    // not explicit: allow "aclMatchCode to allow_t" conversions (for now)
+    allow_t(const aclMatchCode aCode): code(aCode), kind(0) {}
+
+    allow_t(): code(ACCESS_DUNNO), kind(0) {}
+
+    bool operator ==(const aclMatchCode aCode) const {
+        return code == aCode;
+    }
+
+    bool operator !=(const aclMatchCode aCode) const {
+        return !(*this == aCode);
+    }
+
+    operator aclMatchCode() const {
+        return code;
+    }
+
+    aclMatchCode code; ///< ACCESS_* code
+    int kind; ///< which custom access list verb matched
+};
+
 
 inline std::ostream &
 operator <<(std::ostream &o, const allow_t a)