]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
BUG/MEDIUM: map/acl: fix unwanted flags inheritance.
authorEmeric Brun <ebrun@haproxy.com>
Mon, 3 Jul 2017 15:54:23 +0000 (17:54 +0200)
committerWilly Tarreau <w@1wt.eu>
Tue, 4 Jul 2017 08:45:53 +0000 (10:45 +0200)
The bug: Maps/ACLs using the same file/id can mistakenly inherit
their flags from the last declared one.

i.e.

    $ cat haproxy.conf
    listen mylistener
mode http
bind 0.0.0.0:8080

acl myacl1 url -i -f mine.acl
acl myacl2 url -f mine.acl
acl myacl3 url -i -f mine.acl
redirect location / if myacl2
    $ cat mine.acl
    foobar

Shows an unexpected redirect for request 'GET /FOObAR HTTP/1.0\n\n'.

This fix should be backported on mainline branches v1.6 and v1.7.

include/proto/pattern.h
src/acl.c
src/pattern.c

index 9c93db93d254dfbace89a21debabeb1e25a43e15..5b992961444815e4371945ef07729bdb49a1f04d 100644 (file)
@@ -209,7 +209,7 @@ int pattern_read_from_file(struct pattern_head *head, unsigned int refflags, con
 void pattern_init_expr(struct pattern_expr *expr);
 struct pattern_expr *pattern_lookup_expr(struct pattern_head *head, struct pat_ref *ref);
 struct pattern_expr *pattern_new_expr(struct pattern_head *head, struct pat_ref *ref,
-                                      char **err, int *reuse);
+                                      int patflags, char **err, int *reuse);
 struct sample_data **pattern_find_smp(struct pattern_expr *expr, struct pat_ref_elt *elt);
 int pattern_delete(struct pattern_expr *expr, struct pat_ref_elt *ref);
 
index 9b67a611b0f96ead5d9bdac97cae4237c63e1b57..8417c1b5d9e0eb73936d6a979b268e69fb49981d 100644 (file)
--- a/src/acl.c
+++ b/src/acl.c
@@ -536,13 +536,10 @@ struct acl_expr *parse_acl_expr(const char **args, char **err, struct arg_list *
        }
 
        /* Create new pattern expression associated to this reference. */
-       pattern_expr = pattern_new_expr(&expr->pat, ref, err, NULL);
+       pattern_expr = pattern_new_expr(&expr->pat, ref, patflags, err, NULL);
        if (!pattern_expr)
                goto out_free_expr;
 
-       /* Copy the pattern matching and indexing flags. */
-       pattern_expr->mflags = patflags;
-
        /* now parse all patterns */
        while (**args) {
                arg = *args;
index 20593093e876d46d8e1bb47304838c5404072611..a8b56ca5e333221d1e98351c44fa9a13076883ad 100644 (file)
@@ -2065,7 +2065,7 @@ struct pattern_expr *pattern_lookup_expr(struct pattern_head *head, struct pat_r
  * flag <reuse> is set.
  */
 struct pattern_expr *pattern_new_expr(struct pattern_head *head, struct pat_ref *ref,
-                                      char **err, int *reuse)
+                                      int patflags, char **err, int *reuse)
 {
        struct pattern_expr *expr;
        struct pattern_expr_list *list;
@@ -2088,7 +2088,8 @@ struct pattern_expr *pattern_new_expr(struct pattern_head *head, struct pat_ref
                list_for_each_entry(expr, &ref->pat, list)
                        if (expr->pat_head->index     == head->index &&
                            expr->pat_head->parse     == head->parse &&
-                           expr->pat_head->parse_smp == head->parse_smp)
+                           expr->pat_head->parse_smp == head->parse_smp &&
+                           expr->mflags == patflags)
                                break;
                if (&expr->list == &ref->pat)
                        expr = NULL;
@@ -2109,6 +2110,9 @@ struct pattern_expr *pattern_new_expr(struct pattern_head *head, struct pat_ref
                /* Initialize this new expr. */
                pattern_init_expr(expr);
 
+               /* Copy the pattern matching and indexing flags. */
+               expr->mflags = patflags;
+
                /* This new pattern expression reference one of his heads. */
                expr->pat_head = head;
 
@@ -2377,10 +2381,9 @@ int pattern_read_from_file(struct pattern_head *head, unsigned int refflags,
         */
        expr = pattern_lookup_expr(head, ref);
        if (!expr || (expr->mflags != patflags)) {
-               expr = pattern_new_expr(head, ref, err, &reuse);
+               expr = pattern_new_expr(head, ref, patflags, err, &reuse);
                if (!expr)
                        return 0;
-               expr->mflags = patflags;
        }
 
        /* The returned expression may be not empty, because the function