summaryrefslogtreecommitdiff
path: root/regcomp.c
diff options
context:
space:
mode:
authorxtkoba (Tee KOBAYASHI) <xtkoba+ruby@gmail.com>2021-03-15 10:15:10 +0900
committerNobuyoshi Nakada <nobu@ruby-lang.org>2021-03-15 10:17:50 +0900
commit0846c2da457e7523819236ac7da492029b3ef73d (patch)
tree8d424984e1358e5812161be9c51cc16e32dc71de /regcomp.c
parent2a6bfd22468343003463e0cbf91953a01b0dbba5 (diff)
Check backref number buffer overrun [Bug #16376]
Diffstat (limited to 'regcomp.c')
-rw-r--r--regcomp.c21
1 files changed, 12 insertions, 9 deletions
diff --git a/regcomp.c b/regcomp.c
index 7799e1d952..3a438b94c4 100644
--- a/regcomp.c
+++ b/regcomp.c
@@ -1933,7 +1933,7 @@ noname_disable_map(Node** plink, GroupNumRemap* map, int* counter)
}
static int
-renumber_node_backref(Node* node, GroupNumRemap* map)
+renumber_node_backref(Node* node, GroupNumRemap* map, const int num_mem)
{
int i, pos, n, old_num;
int *backs;
@@ -1949,6 +1949,7 @@ renumber_node_backref(Node* node, GroupNumRemap* map)
backs = bn->back_dynamic;
for (i = 0, pos = 0; i < old_num; i++) {
+ if (backs[i] > num_mem) return ONIGERR_INVALID_BACKREF;
n = map[backs[i]].new_val;
if (n > 0) {
backs[pos] = n;
@@ -1961,7 +1962,7 @@ renumber_node_backref(Node* node, GroupNumRemap* map)
}
static int
-renumber_by_map(Node* node, GroupNumRemap* map)
+renumber_by_map(Node* node, GroupNumRemap* map, const int num_mem)
{
int r = 0;
@@ -1969,28 +1970,30 @@ renumber_by_map(Node* node, GroupNumRemap* map)
case NT_LIST:
case NT_ALT:
do {
- r = renumber_by_map(NCAR(node), map);
+ r = renumber_by_map(NCAR(node), map, num_mem);
} while (r == 0 && IS_NOT_NULL(node = NCDR(node)));
break;
case NT_QTFR:
- r = renumber_by_map(NQTFR(node)->target, map);
+ r = renumber_by_map(NQTFR(node)->target, map, num_mem);
break;
case NT_ENCLOSE:
{
EncloseNode* en = NENCLOSE(node);
- if (en->type == ENCLOSE_CONDITION)
+ if (en->type == ENCLOSE_CONDITION) {
+ if (en->regnum > num_mem) return ONIGERR_INVALID_BACKREF;
en->regnum = map[en->regnum].new_val;
- r = renumber_by_map(en->target, map);
+ }
+ r = renumber_by_map(en->target, map, num_mem);
}
break;
case NT_BREF:
- r = renumber_node_backref(node, map);
+ r = renumber_node_backref(node, map, num_mem);
break;
case NT_ANCHOR:
if (NANCHOR(node)->target)
- r = renumber_by_map(NANCHOR(node)->target, map);
+ r = renumber_by_map(NANCHOR(node)->target, map, num_mem);
break;
default:
@@ -2052,7 +2055,7 @@ disable_noname_group_capture(Node** root, regex_t* reg, ScanEnv* env)
r = noname_disable_map(root, map, &counter);
if (r != 0) return r;
- r = renumber_by_map(*root, map);
+ r = renumber_by_map(*root, map, env->num_mem);
if (r != 0) return r;
for (i = 1, pos = 1; i <= env->num_mem; i++) {