Follow-up to d34a6664
authorFather Chrysostomos <sprout@cpan.org>
Fri, 3 Jun 2011 21:20:10 +0000 (14:20 -0700)
committerFather Chrysostomos <sprout@cpan.org>
Fri, 3 Jun 2011 21:20:10 +0000 (14:20 -0700)
As Nicholas Clark wrote in
nntp://nntp.perl.org/20110603192458.GZ2604@plum.flirble.org:

> $ valgrind ./perl -Ilib 91880.pl
> ==5542== Memcheck, a memory error detector
...
> I think that the problem is that this code in S_run_user_filter()
>
>  ENTER_with_name("call_filter_sub");
>  SAVEGENERICSV(GvSV(PL_defgv));
>  SAVETMPS;
>  EXTEND(SP, 2);
>
>
> is putting an action on the save stack to write to an address within
> the GP of PL_defgv. However, the perl code run about 10 lines later
> frees up the GP of PL_defgv, so the scope stack now has a dangling
> pointer. 12 lines later at scope exit, the scope stack unwinding
> writes to the pointer, and nasal daemons emerge.

This commit precedes the SAVEGENERICSV with a call to save_gp, to make
sure the GP is not freed (and then a call to GvINTRO_off [set by
save_gp], so that subsequent glob assignments are not implicitly
localised).

This basically emulates what happens with â€˜local *_ = \$some_scalar’,
but without the extra intermediate RV.

pp_ctl.c

index 4413587..0c51e28 100644 (file)
--- a/pp_ctl.c
+++ b/pp_ctl.c
@@ -5273,6 +5273,8 @@ S_run_user_filter(pTHX_ int idx, SV *buf_sv, int maxlen)
        int count;
 
        ENTER_with_name("call_filter_sub");
+       save_gp(PL_defgv, 0);
+       GvINTRO_off(PL_defgv);
        SAVEGENERICSV(GvSV(PL_defgv));
        SAVETMPS;
        EXTEND(SP, 2);