Perl / perl5

🐪 The Perl programming language
https://dev.perl.org/perl5/
Other
1.91k stars 542 forks source link

null pointer dereference in Perl_sv_setpvn at sv.c:4896 #15287

Open p5pRT opened 8 years ago

p5pRT commented 8 years ago

Migrated from rt.perl.org#127956 (status was 'open')

Searchable as RT127956$

p5pRT commented 8 years ago

From @geeknik

While fuzzing Perl v5.24.0-RC1-2-gde1d2c7 with American Fuzzy Lop\, I discovered that perl -e '$0=$.^=*.=$0=0' causes a null pointer dereference and crash. This crash affects Perl v5.14.2 as well.

Program received signal SIGSEGV\, Segmentation fault. Perl_sv_setpvn (sv=sv@​entry=0x1201948\, ptr=ptr@​entry=0xed4da7 ""\, len=len@​entry=0) at sv.c​:4896 4896 dptr[len] = '\0'; (gdb) bt #0 Perl_sv_setpvn (sv=sv@​entry=0x1201948\, ptr=ptr@​entry=0xed4da7 ""\, len=len@​entry=0) at sv.c​:4896 #1 0x0000000000c2a6f3 in Perl_do_vop (optype=optype@​entry=93\, sv=sv@​entry=0x1201948\,   left=left@​entry=0x1201948\, right=right@​entry=0x1201930) at doop.c​:1011 #2 0x0000000000a763a1 in Perl_pp_bit_or () at pp.c​:2491 #3 0x00000000007ff5d4 in Perl_runops_debug () at dump.c​:2239 #4 0x0000000000539034 in S_run_body (oldscope=1) at perl.c​:2483 #5 perl_run (my_perl=\) at perl.c​:2406 #6 0x000000000042eac8 in main (argc=3\, argv=0x7fffffffe658\, env=0x7fffffffe678) at perlmain.c​:116 (gdb) list 4891 } 4892 SvUPGRADE(sv\, SVt_PV); 4893 4894 dptr = SvGROW(sv\, len + 1); 4895 Move(ptr\,dptr\,len\,char); 4896 dptr[len] = '\0'; 4897 SvCUR_set(sv\, len); 4898 (void)SvPOK_only_UTF8(sv); /* validate pointer */ 4899 SvTAINT(sv); 4900 if (SvTYPE(sv) == SVt_PVCV) CvAUTOLOAD_off(sv);

p5pRT commented 8 years ago

From @Smylers

Brian Carpenter writes​:

While fuzzing Perl v5.24.0-RC1-2-gde1d2c7 with American Fuzzy Lop\, I discovered that perl -e '$0=$.^=*.=$0=0' causes a null pointer dereference and crash. This crash affects Perl v5.14.2 as well.

Smaller case that still yields the crash\, without special variables​:

  perl -e '$x ^= *x = 0'

Also​:  
  perl -e '$x |= *x = 0'

But not​:

  perl -e '$x &= *x = 0'   Can't coerce UNKNOWN to string in bitwise and (&) at -e line 1.

Smylers -- http​://twitter.com/Smylers2

p5pRT commented 8 years ago

The RT System itself - Status changed from 'new' to 'open'

p5pRT commented 8 years ago

From @cpansprout

On Fri Apr 22 01​:38​:07 2016\, smylers@​stripey.com wrote​:

Brian Carpenter writes​:

While fuzzing Perl v5.24.0-RC1-2-gde1d2c7 with American Fuzzy Lop\, I discovered that perl -e '$0=$.^=*.=$0=0' causes a null pointer dereference and crash. This crash affects Perl v5.14.2 as well.

Smaller case that still yields the crash\, without special variables​:

perl -e '$x ^= *x = 0'

Also​:

perl -e '$x |= *x = 0'

But not​:

perl -e '$x &= *x = 0' Can't coerce UNKNOWN to string in bitwise and (&) at -e line 1.

That UNKNOWN is an internal fallback value that should never be seen. I would say this last case is just as buggy. It smells like a stack issue.

--

Father Chrysostomos

p5pRT commented 8 years ago

From zefram@fysh.org

Brian Carpenter wrote​:

perl -e '$0=$.^=*.=$0=0'

This reduces to

  perl -e '$z ^= *z=0'

which looks almost exactly like [perl #127934]. That one used *= and asserted\, whereas this one uses ^= and segvs. They're probably the same bug underneath. |= and .= also segv​: the pattern seems to be that numeric operations assert and string operations segv on handling the string buffer.

-zefram

p5pRT commented 8 years ago

From @cpansprout

On Fri Apr 22 08​:36​:02 2016\, zefram@​fysh.org wrote​:

Brian Carpenter wrote​:

perl -e '$0=$.^=*.=$0=0'

This reduces to

    perl \-e '$z ^= \*z=0'

which looks almost exactly like [perl #127934]. That one used *= and asserted\, whereas this one uses ^= and segvs. They're probably the same bug underneath. |= and .= also segv​: the pattern seems to be that numeric operations assert and string operations segv on handling the string buffer.

I am pretty sure these are both stack issues. The *z=0 frees *z{SCALAR} while the latter is on the stack.

$ perl -le 'print $^V' v5.12.4 $ perl -e '$z ^= *z=0' Segmentation fault​: 11 $ perl -e '*b=*z; $z ^= *z=0; print "$b\n"' *main​::0

--

Father Chrysostomos

p5pRT commented 8 years ago

From @geeknik

I just ran into this issue again while fuzzing v5.25.1-152-g81b22c1.

p5pRT commented 8 years ago

From [Unknown Contact. See original ticket]

I just ran into this issue again while fuzzing v5.25.1-152-g81b22c1.