This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
RT#130624: heap-use-after-free in 4-arg substr
authorAaron Crane <arc@cpan.org>
Tue, 24 Jan 2017 23:39:40 +0000 (23:39 +0000)
committerDavid Mitchell <davem@iabyn.com>
Mon, 27 Feb 2017 12:14:59 +0000 (12:14 +0000)
pp.c
t/op/substr.t

diff --git a/pp.c b/pp.c
index 62316fc..a640995 100644 (file)
--- a/pp.c
+++ b/pp.c
@@ -3396,8 +3396,10 @@ PP(pp_substr)
        tmps = SvPV_force_nomg(sv, curlen);
        if (DO_UTF8(repl_sv) && repl_len) {
            if (!DO_UTF8(sv)) {
+                /* Upgrade the dest, and recalculate tmps in case the buffer
+                 * got reallocated; curlen may also have been changed */
                sv_utf8_upgrade_nomg(sv);
-               curlen = SvCUR(sv);
+               tmps = SvPV_nomg(sv, curlen);
            }
        }
        else if (DO_UTF8(sv))
index a8abed8..3c7f0eb 100644 (file)
@@ -22,7 +22,7 @@ $SIG{__WARN__} = sub {
      }
 };
 
-plan(391);
+plan(393);
 
 run_tests() unless caller;
 
@@ -880,3 +880,15 @@ is($destroyed, 1, 'Timely scalar destruction with lvalue substr');
 
 # failed with ASAN
 fresh_perl_is('$0 = "/usr/bin/perl"; substr($0, 0, 0, $0)', '', {}, "(perl #129340) substr() with source in target");
+
+
+# [perl #130624] - heap-use-after-free, observable under asan
+{
+    my $x = "\xE9zzzz";
+    my $y = "\x{100}";
+    my $z = substr $x, 0, 1, $y;
+    is $z, "\xE9",        "RT#130624: heap-use-after-free in 4-arg substr (ret)";
+    is $x, "\x{100}zzzz", "RT#130624: heap-use-after-free in 4-arg substr (targ)";
+}
+
+