Whamcloud - gitweb
LU-15130 nrs: null pointer dereference in nrs_tbf_id_parse 91/45291/4
authorEtienne AUJAMES <etienne.aujames@cea.fr>
Tue, 19 Oct 2021 14:10:43 +0000 (16:10 +0200)
committerOleg Drokin <green@whamcloud.com>
Fri, 7 Jan 2022 00:59:16 +0000 (00:59 +0000)
cfs_gettok() set next->ls_str to NULL if no delimiter is found but
it does not update next->ls_len to 0.
We have to check if next->ls_str is null inside nrs_tbf_id_parse()
to verify if the tbf expression is valid.

* Reproducer *
lctl set_param  mds.MDS.mdt.nrs_tbf_rule="start tbf_name gid{500}
rate=100"

This patch fix cfs_gettok() to update "next->ls_len = 0;" if no
delimiter is found.

Signed-off-by: Etienne AUJAMES <eaujames@ddn.com>
Change-Id: Iaa4eb5085262cee547ea3a944ddb94c6df1f8aa3
Reviewed-on: https://review.whamcloud.com/45291
Tested-by: jenkins <devops@whamcloud.com>
Reviewed-by: Andreas Dilger <adilger@whamcloud.com>
Tested-by: Maloo <maloo@whamcloud.com>
Reviewed-by: Li Xi <lixi@ddn.com>
Reviewed-by: Oleg Drokin <green@whamcloud.com>
libcfs/libcfs/libcfs_string.c
libcfs/libcfs/util/string.c
lustre/ptlrpc/nrs_tbf.c

index 5549417..7ba00df 100644 (file)
@@ -151,6 +151,7 @@ cfs_gettok(struct cfs_lstr *next, char delim, struct cfs_lstr *res)
                /* there is no the delimeter in the string */
                end = next->ls_str + next->ls_len;
                next->ls_str = NULL;
                /* there is no the delimeter in the string */
                end = next->ls_str + next->ls_len;
                next->ls_str = NULL;
+               next->ls_len = 0;
        } else {
                next->ls_str = end + 1;
                next->ls_len -= (end - res->ls_str + 1);
        } else {
                next->ls_str = end + 1;
                next->ls_len -= (end - res->ls_str + 1);
index 9e92339..700f002 100644 (file)
@@ -84,6 +84,7 @@ cfs_gettok(struct cfs_lstr *next, char delim, struct cfs_lstr *res)
                /* there is no the delimeter in the string */
                end = next->ls_str + next->ls_len;
                next->ls_str = NULL;
                /* there is no the delimeter in the string */
                end = next->ls_str + next->ls_len;
                next->ls_str = NULL;
+               next->ls_len = 0;
        } else {
                next->ls_str = end + 1;
                next->ls_len -= (end - res->ls_str + 1);
        } else {
                next->ls_str = end + 1;
                next->ls_len -= (end - res->ls_str + 1);
index 37edf58..2b819e7 100644 (file)
@@ -929,8 +929,8 @@ static int nrs_tbf_check_id_value(struct cfs_lstr *src, char *key)
        rc = cfs_gettok(src, '=', &res);
        if (rc == 0 || res.ls_len != keylen ||
            strncmp(res.ls_str, key, keylen) != 0 ||
        rc = cfs_gettok(src, '=', &res);
        if (rc == 0 || res.ls_len != keylen ||
            strncmp(res.ls_str, key, keylen) != 0 ||
-           src->ls_len <= 2 || src->ls_str[0] != '{' ||
-           src->ls_str[src->ls_len - 1] != '}')
+           !src->ls_str || src->ls_len <= 2 ||
+           src->ls_str[0] != '{' || src->ls_str[src->ls_len - 1] != '}')
                return -EINVAL;
 
        /* Skip '{' and '}' */
                return -EINVAL;
 
        /* Skip '{' and '}' */
@@ -1840,8 +1840,8 @@ nrs_tbf_expression_parse(struct cfs_lstr *src, struct list_head *cond_list)
                return -ENOMEM;
 
        rc = cfs_gettok(src, NRS_TBF_EXPRESSION_DELIM, &field);
                return -ENOMEM;
 
        rc = cfs_gettok(src, NRS_TBF_EXPRESSION_DELIM, &field);
-       if (rc == 0 || src->ls_len <= 2 || src->ls_str[0] != '{' ||
-           src->ls_str[src->ls_len - 1] != '}')
+       if (rc == 0 || !src->ls_str || src->ls_len <= 2 ||
+           src->ls_str[0] != '{' || src->ls_str[src->ls_len - 1] != '}')
                GOTO(out, rc = -EINVAL);
 
        /* Skip '{' and '}' */
                GOTO(out, rc = -EINVAL);
 
        /* Skip '{' and '}' */