Fix JIT compilation of conditional blocks whose assertion is converted to (*FAIL).

This commit is contained in:
Zoltán Herczeg 2015-03-24 08:43:52 +00:00
parent 4e61019ffe
commit 69cda6bc70
3 changed files with 9 additions and 3 deletions

View File

@ -14,6 +14,9 @@ error. This bug was discovered by the LLVM fuzzer.
4. Implemented pcre2_callout_enumerate(). 4. Implemented pcre2_callout_enumerate().
5. Fix JIT compilation of conditional blocks whose assertion
is converted to (*FAIL). E.g: /(?(?!))/.
Version 10.10 06-March-2015 Version 10.10 06-March-2015
--------------------------- ---------------------------

View File

@ -7044,7 +7044,7 @@ if (SLJIT_UNLIKELY(opcode == OP_COND || opcode == OP_SCOND))
{ {
SLJIT_COMPILE_ASSERT(OP_DNRREF == OP_RREF + 1 && OP_FALSE == OP_RREF + 2 && OP_TRUE == OP_RREF + 3, SLJIT_COMPILE_ASSERT(OP_DNRREF == OP_RREF + 1 && OP_FALSE == OP_RREF + 2 && OP_TRUE == OP_RREF + 3,
compile_time_checks_must_be_grouped_together); compile_time_checks_must_be_grouped_together);
has_alternatives = (*matchingpath >= OP_RREF && *matchingpath <= OP_TRUE) ? FALSE : TRUE; has_alternatives = ((*matchingpath >= OP_RREF && *matchingpath <= OP_TRUE) || *matchingpath == OP_FAIL) ? FALSE : TRUE;
} }
if (SLJIT_UNLIKELY(opcode == OP_COND) && (*cc == OP_KETRMAX || *cc == OP_KETRMIN)) if (SLJIT_UNLIKELY(opcode == OP_COND) && (*cc == OP_KETRMAX || *cc == OP_KETRMIN))
@ -7303,7 +7303,7 @@ if (opcode == OP_COND || opcode == OP_SCOND)
add_jump(compiler, &(BACKTRACK_AS(bracket_backtrack)->u.condfailed), JUMP(SLJIT_ZERO)); add_jump(compiler, &(BACKTRACK_AS(bracket_backtrack)->u.condfailed), JUMP(SLJIT_ZERO));
matchingpath += 1 + 2 * IMM2_SIZE; matchingpath += 1 + 2 * IMM2_SIZE;
} }
else if (*matchingpath >= OP_RREF && *matchingpath <= OP_TRUE) else if ((*matchingpath >= OP_RREF && *matchingpath <= OP_TRUE) || *matchingpath == OP_FAIL)
{ {
/* Never has other case. */ /* Never has other case. */
BACKTRACK_AS(bracket_backtrack)->u.condfailed = NULL; BACKTRACK_AS(bracket_backtrack)->u.condfailed = NULL;
@ -7314,7 +7314,7 @@ if (opcode == OP_COND || opcode == OP_SCOND)
stacksize = 1; stacksize = 1;
matchingpath++; matchingpath++;
} }
else if (*matchingpath == OP_FALSE) else if (*matchingpath == OP_FALSE || *matchingpath == OP_FAIL)
stacksize = 0; stacksize = 0;
else if (*matchingpath == OP_RREF) else if (*matchingpath == OP_RREF)
{ {

View File

@ -647,6 +647,9 @@ static struct regression_test_case regression_test_cases[] = {
{ MU, A, 0, 0, "(?P<Name>a)?(?P<Name2>b)?(?(Name)c|d)+?dd", "bcabcacdb bdddd" }, { MU, A, 0, 0, "(?P<Name>a)?(?P<Name2>b)?(?(Name)c|d)+?dd", "bcabcacdb bdddd" },
{ MU, A, 0, 0, "(?P<Name>a)?(?P<Name2>b)?(?(Name)c|d)+l", "ababccddabdbccd abcccl" }, { MU, A, 0, 0, "(?P<Name>a)?(?P<Name2>b)?(?(Name)c|d)+l", "ababccddabdbccd abcccl" },
{ MU, A, 0, 0, "((?:a|aa)(?(1)aaa))x", "aax" }, { MU, A, 0, 0, "((?:a|aa)(?(1)aaa))x", "aax" },
{ MU, A, 0, 0, "(?(?!)a|b)", "ab" },
{ MU, A, 0, 0, "(?(?!)a)", "ab" },
{ MU, A, 0, 0 | F_NOMATCH, "(?(?!)a|b)", "ac" },
/* Set start of match. */ /* Set start of match. */
{ MU, A, 0, 0, "(?:\\Ka)*aaaab", "aaaaaaaa aaaaaaabb" }, { MU, A, 0, 0, "(?:\\Ka)*aaaab", "aaaaaaaa aaaaaaabb" },