[pcre-dev] [Bug 1803] segfault in pcre jit when running twig…

Top Page
Delete this message
Author: admin
Date:  
To: pcre-dev
Subject: [pcre-dev] [Bug 1803] segfault in pcre jit when running twig test suite (PHP7)
https://bugs.exim.org/show_bug.cgi?id=1803

--- Comment #29 from Zoltan Herczeg <hzmester@???> ---
> I don't see any problem. So I'm not 100% sure it's this pattern in this
> execution that is bad, but some state somewhere (could be php, could be
> libpcre) is getting corrupted.


I agree. This is my opinion as well.

> I also noticed that for UTF8 specificaly, there is another pcre_exec that
> occurs (l#1853).


I also mentioned this before. I had the feeling that the 2,4 offset pair is
coming from this pcre_exec (unfortunately both pcre_execs shares the same
ovector). This is confirmed now. And count really is stored in $eax.

This is the result of the last pcre_exec:

> (gdb) print offsets[0]
> $130 = 2
> (gdb) print offsets[1]
> $131 = 4
> (gdb) printf "0x%x\n", g_notempty
> 0x0
> (gdb) step
> 1794            if (count == 0) {
> (gdb) print $eax
> $132 = 0
> (gdb) print offsets[0]
> $133 = 2
> (gdb) print offsets[1]
> $134 = 4


This confirms the "ovector is not changed" theory. The zero return value means
there is not enough space in the ovector, and offsets are not updated. More
precisely it seems as if 0 is passed for the length of offsets vector
(size_offsets is changed to zero somehow?).

Because count is zero:

if (count == 0) {
    php_error_docref(NULL,E_NOTICE, "Matched, but too many substrings");
    count = size_offsets/3;
}


count got a new value. However, if size_offsets would be changed to 0, count
would be zero again (0/3=0).

And the following condition (where the segfault happens) would not be
fulfilled:

if (count > 0 && (offsets[1] - offsets[0] >= 0)) {

To make things even more confusing, pcre_exec runs correctly during the first
run:

> 1794            if (count == 0) {
> (gdb) print $eax
> $122 = 1
> (gdb) print offsets[0]
> $123 = 2
> (gdb) print offsets[1]
> $124 = 2


Here, there was enough space so the return value was 1, and offsets vector was
updated (2,2 is the correct result for the first run).

I think we should focus on the size_offsets variable, and what is passed to
pcre_exec. It seems to me that although size_offsets did not change its value
(regardless please print it), somehow 0 is passed to pcre_exec. Or the passed
value is overwritten to zero later (buffer overflow?). Could you enter to
pcre_exec and print the arguments? Especially the size of the ovector
(offsetcount). A watchpoint could help to find where the value is changed if
the argument is correct.

--
You are receiving this mail because:
You are on the CC list for the bug.