92 lines
3.4 KiB
Diff
92 lines
3.4 KiB
Diff
|
From 439a3bfe85749ea9eca31372daec5705acaa3db1 Mon Sep 17 00:00:00 2001
|
|||
|
From: Karl Williamson <khw@cpan.org>
|
|||
|
Date: Sat, 24 Aug 2019 19:17:19 -0600
|
|||
|
Subject: [PATCH] PATCH: [perl #134325] Heap buffer overflow
|
|||
|
MIME-Version: 1.0
|
|||
|
Content-Type: text/plain; charset=UTF-8
|
|||
|
Content-Transfer-Encoding: 8bit
|
|||
|
|
|||
|
This was the result of trying to continue to parse after realizing that
|
|||
|
we were going to have to reparse using long jumps. This continuing only
|
|||
|
happened when we realized we were going to have to reparse in order to
|
|||
|
count parentheses anyway, and it was an attempt to save a pass in the
|
|||
|
regex compiler, as without doing the continuing we'd restart the parse
|
|||
|
to use long jumps from the beginning, and then when finished, would
|
|||
|
restart the parse to count the parentheses.
|
|||
|
|
|||
|
However, in most cases this doesn't help, as when we get towards the end
|
|||
|
of the parse (as in the test case in this ticket), we need the long
|
|||
|
jump, and will segfault because we don't have it. So we need the extra
|
|||
|
pass anyway.
|
|||
|
|
|||
|
So this commit restarts the parse as soon as we discover we are going to
|
|||
|
need longjumps
|
|||
|
|
|||
|
Signed-off-by: Petr Písař <ppisar@redhat.com>
|
|||
|
---
|
|||
|
regcomp.c | 8 ++------
|
|||
|
t/re/pat.t | 14 ++++++++++++--
|
|||
|
2 files changed, 14 insertions(+), 8 deletions(-)
|
|||
|
|
|||
|
diff --git a/regcomp.c b/regcomp.c
|
|||
|
index 05dd9a5e7b..abb029f8c0 100644
|
|||
|
--- a/regcomp.c
|
|||
|
+++ b/regcomp.c
|
|||
|
@@ -377,12 +377,8 @@ struct RExC_state_t {
|
|||
|
#define REQUIRE_BRANCHJ(flagp, restart_retval) \
|
|||
|
STMT_START { \
|
|||
|
RExC_use_BRANCHJ = 1; \
|
|||
|
- if (LIKELY(! IN_PARENS_PASS)) { \
|
|||
|
- /* No need to restart the parse immediately if we're \
|
|||
|
- * going to reparse anyway to count parens */ \
|
|||
|
- *flagp |= RESTART_PARSE; \
|
|||
|
- return restart_retval; \
|
|||
|
- } \
|
|||
|
+ *flagp |= RESTART_PARSE; \
|
|||
|
+ return restart_retval; \
|
|||
|
} STMT_END
|
|||
|
|
|||
|
/* Until we have completed the parse, we leave RExC_total_parens at 0 or
|
|||
|
diff --git a/t/re/pat.t b/t/re/pat.t
|
|||
|
index e54affcd94..6a868f4bcd 100644
|
|||
|
--- a/t/re/pat.t
|
|||
|
+++ b/t/re/pat.t
|
|||
|
@@ -25,7 +25,7 @@ BEGIN {
|
|||
|
skip_all('no re module') unless defined &DynaLoader::boot_DynaLoader;
|
|||
|
skip_all_without_unicode_tables();
|
|||
|
|
|||
|
-plan tests => 863; # Update this when adding/deleting tests.
|
|||
|
+plan tests => 864; # Update this when adding/deleting tests.
|
|||
|
|
|||
|
run_tests() unless caller;
|
|||
|
|
|||
|
@@ -33,7 +33,6 @@ run_tests() unless caller;
|
|||
|
# Tests start here.
|
|||
|
#
|
|||
|
sub run_tests {
|
|||
|
-
|
|||
|
my $sharp_s = uni_to_native("\xdf");
|
|||
|
|
|||
|
{
|
|||
|
@@ -2105,6 +2104,17 @@ x{0c!}\;\;îçÿ |