]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
[MEDIUM] restrict the set of allowed characters for identifiers
authorWilly Tarreau <w@1wt.eu>
Sun, 2 Dec 2007 17:45:09 +0000 (18:45 +0100)
committerWilly Tarreau <w@1wt.eu>
Sun, 2 Dec 2007 17:45:09 +0000 (18:45 +0100)
In order to avoid issues in the future, we want to restrict
the set of allowed characters for identifiers. Starting from
now, only A-Z, a-z, 0-9, '-', '_', '.' and ':' will be allowed
for a proxy, a server or an ACL name.

A test file has been added to check the restriction.

include/common/standard.h
src/acl.c
src/cfgparse.c
src/standard.c
tests/test-valid-names.cfg [new file with mode: 0644]

index 80f6d2a28acb7f04def69df832ffe695c5ae408c..0dde6db37b358a1071ca14caf7be89bae2bd5cb6 100644 (file)
@@ -117,6 +117,13 @@ extern const char *limit_r(unsigned long n, char *buffer, int size, const char *
  */
 extern int ishex(char s);
 
+/*
+ * Checks <name> for invalid characters. Valid chars are [A-Za-z0-9_:.-]. If an
+ * invalid character is found, a pointer to it is returned. If everything is
+ * fine, NULL is returned.
+ */
+extern const char *invalid_char(const char *name);
+
 /*
  * converts <str> to a struct sockaddr_in* which is locally allocated.
  * The format is "addr:port", where "addr" can be a dotted IPv4 address,
index f7ac06c0e824481a43de8a8765ce04a2399bf8a7..aa095c5bd2909a112bf73a8689de6e74a156b568 100644 (file)
--- a/src/acl.c
+++ b/src/acl.c
@@ -580,6 +580,9 @@ struct acl *parse_acl(const char **args, struct list *known_acl)
        struct acl_expr *acl_expr;
        char *name;
 
+       if (invalid_char(*args))
+               goto out_return;
+
        acl_expr = parse_acl_expr(args + 1);
        if (!acl_expr)
                goto out_return;
index 232ae1c7bf99d29dac3bec0c2d0aef2a0a471fb0..b64d4c6b47f56d9c6d019f43a0b5b059fb2b959d 100644 (file)
@@ -534,6 +534,13 @@ int cfg_parse_listen(const char *file, int linenum, char **args)
                        return -1;
                }
 
+               err = invalid_char(args[1]);
+               if (err) {
+                       Alert("parsing [%s:%d] : character '%c' is not permitted in '%s' name '%s'.\n",
+                             file, linenum, *err, args[0], args[1]);
+                       return -1;
+               }
+
                for (curproxy = proxy; curproxy != NULL; curproxy = curproxy->next) {
                        /*
                         * If there are two proxies with the same name only following
@@ -759,6 +766,13 @@ int cfg_parse_listen(const char *file, int linenum, char **args)
                curproxy->state = PR_STNEW;
        }
        else if (!strcmp(args[0], "acl")) {  /* add an ACL */
+               err = invalid_char(args[1]);
+               if (err) {
+                       Alert("parsing [%s:%d] : character '%c' is not permitted in acl name '%s'.\n",
+                             file, linenum, *err, args[1]);
+                       return -1;
+               }
+
                if (parse_acl((const char **)args + 1, &curproxy->acl) == NULL) {
                        Alert("parsing [%s:%d] : error detected while parsing ACL '%s'.\n",
                              file, linenum, args[1]);
@@ -1414,6 +1428,14 @@ int cfg_parse_listen(const char *file, int linenum, char **args)
                              file, linenum, args[0]);
                        return -1;
                }
+
+               err = invalid_char(args[1]);
+               if (err) {
+                       Alert("parsing [%s:%d] : character '%c' is not permitted in server name '%s'.\n",
+                             file, linenum, *err, args[1]);
+                       return -1;
+               }
+
                if ((newsrv = (struct server *)calloc(1, sizeof(struct server))) == NULL) {
                        Alert("parsing [%s:%d] : out of memory.\n", file, linenum);
                        return -1;
index 0b1629659dc083300d3190aff065f2d6f9dcd493..07aa5e48d8234dd12dcab9fd5f016d11fce15f06 100644 (file)
@@ -10,6 +10,7 @@
  *
  */
 
+#include <ctype.h>
 #include <netdb.h>
 #include <stdlib.h>
 #include <string.h>
@@ -98,6 +99,24 @@ int ishex(char s)
        return 0;
 }
 
+/*
+ * Checks <name> for invalid characters. Valid chars are [A-Za-z0-9_:.-]. If an
+ * invalid character is found, a pointer to it is returned. If everything is
+ * fine, NULL is returned.
+ */
+const char *invalid_char(const char *name)
+{
+       if (!*name)
+               return name;
+
+       while (*name) {
+               if (!isalnum(*name) && *name != '.' && *name != ':' &&
+                   *name != '_' && *name != '-')
+                       return name;
+               name++;
+       }
+       return NULL;
+}
 
 /*
  * converts <str> to a struct sockaddr_in* which is locally allocated.
diff --git a/tests/test-valid-names.cfg b/tests/test-valid-names.cfg
new file mode 100644 (file)
index 0000000..1842a78
--- /dev/null
@@ -0,0 +1,37 @@
+# This is a test configuration.
+# It checks instances, servers and acl names.
+
+listen         valid_listen1
+               bind            :8000
+               clitimeout      5000
+               contimeout      5000
+               srvtimeout      5000
+               balance         roundrobin
+               server          srv1 127.0.0.1:80
+
+frontend       www.valid-frontend.net:80
+               bind            :8001
+               clitimeout      5000
+               acl host_www.valid-frontend.net:80 hdr(host) www.valid-frontend.net
+
+backend                Valid_BK-1
+               contimeout      5000
+               srvtimeout      5000
+               balance         roundrobin
+               server          bk1_srv-1:80 127.0.0.1:80
+
+frontend       www.test-frontend.net:8002/invalid
+               bind            :8002
+               clitimeout      5000
+
+frontend       ft1_acl
+               bind            :8003
+               clitimeout      5000
+               acl invalid!name url /
+
+backend                bk2_srv
+               contimeout      5000
+               srvtimeout      5000
+               balance         roundrobin
+               server          bk2/srv-1 127.0.0.1:80
+