@@ -530,7 +530,7 @@ my $DEBUG_LEAKING_SCALARS = $Config{ccflags} =~ m/-DDEBUG_LEAKING_SCALARS/;
530530my $CPERL52 = ( $Config {usecperl } and $] >= 5.022002 ); # sv_objcount, AvSTATIC, sigs
531531my $CPERL51 = ( $Config {usecperl } );
532532my $PERL524 = ( $] >= 5.023005 ); # xpviv sharing assertion
533- my $PERL522 = ( $] >= 5.021006 ); # PADNAMELIST, IsCOW, padname_with_str
533+ my $PERL522 = ( $] >= 5.021006 ); # PADNAMELIST, IsCOW, padname_with_str, compflags
534534my $PERL518 = ( $] >= 5.017010 );
535535my $PERL514 = ( $] >= 5.013002 );
536536my $PERL512 = ( $] >= 5.011 );
@@ -2502,6 +2502,21 @@ sub B::COP::save {
25022502 savesym( $op , " (OP*)&cop_list[$ix ]" );
25032503}
25042504
2505+ # if REGCOMP can be called in init or deferred in init1
2506+ sub re_does_swash {
2507+ my ($qstr , $pmflags ) = @_ ;
2508+ # SWASHNEW, now needing a multideref GV. 0x5000000 is just a hack. can be more
2509+ if (($] >= 5.021006 and ($pmflags & 0x5000000 == 0x5000000))
2510+ # or any unicode property (#253). Note: \p{} breaks #242
2511+ or ($qstr =~ / \\ P\{ / )
2512+ )
2513+ {
2514+ return 1;
2515+ } else {
2516+ return 0;
2517+ }
2518+ }
2519+
25052520sub B ::PMOP::save {
25062521 my ( $op , $level , $fullname ) = @_ ;
25072522 my ($replrootfield , $replstartfield , $gvsym ) = (' NULL' , ' NULL' );
@@ -2602,6 +2617,7 @@ sub B::PMOP::save {
26022617 unless $B::C::optimize_ppaddr ;
26032618 my $re = $op -> precomp;
26042619 if ( defined ($re ) ) {
2620+ my $initpm = $init ;
26052621 $Regexp {$$op } = $op ;
26062622 if ($PERL510 ) {
26072623 # TODO minor optim: fix savere( $re ) to avoid newSVpvn;
@@ -2622,10 +2638,9 @@ sub B::PMOP::save {
26222638 # some pm need early init (242), SWASHNEW needs some late GVs (GH#273)
26232639 # esp with 5.22 multideref init. i.e. all \p{} \N{}, \U, /i, ...
26242640 # But XSLoader and utf8::SWASHNEW itself needs to be early.
2625- my $initpm = $init ;
2626- if (($utf8 and $] >= 5.013009 and $pmflags & 4) # needs SWASHNEW (case fold)
2627- # also SWASHNEW, now needing a multideref GV. 0x5000000 is just a hack. can be more
2628- or ($] >= 5.021006 and ($pmflags & 0x5000000 == 0x5000000))) {
2641+ if (($utf8 and $] >= 5.013009 and ($pmflags & 4 == 4)) # needs SWASHNEW (case fold)
2642+ or re_does_swash($qre , $pmflags ))
2643+ {
26292644 $initpm = $init1 ;
26302645 warn sprintf (" deferred PMOP %s %s 0x%x \n " , $qre , $fullname , $pmflags ) if $debug {sv };
26312646 } else {
@@ -3328,14 +3343,16 @@ sub B::REGEXP::save {
33283343 my $ix = $svsect -> index ;
33293344 warn " Saving RX $cstr to sv_list[$ix ]\n " if $debug {rx } or $debug {sv };
33303345 if ($] > 5.011) {
3346+ my $pmflags = $PERL522 ? $sv -> compflags : $sv -> EXTFLAGS;
3347+ my $initpm = re_does_swash($cstr , $pmflags ) ? $init1 : $init ;
33313348 if ($PERL518 and $sv -> EXTFLAGS & RXf_EVAL_SEEN) {
3332- $init -> add(" PL_hints |= HINT_RE_EVAL;" );
3349+ $initpm -> add(" PL_hints |= HINT_RE_EVAL;" );
33333350 }
3334- $init -> add(# replace sv_any->XPV with struct regexp. need pv and extflags
3351+ $initpm -> add(# replace sv_any->XPV with struct regexp. need pv and extflags
33353352 sprintf (" SvANY(&sv_list[%d ]) = SvANY(CALLREGCOMP(newSVpvn(%s , %d ), 0x%x ));" ,
3336- $ix , $cstr , $cur , $sv -> EXTFLAGS ));
3353+ $ix , $cstr , $cur , $pmflags ));
33373354 if ($PERL518 and $sv -> EXTFLAGS & RXf_EVAL_SEEN) {
3338- $init -> add(" PL_hints &= ~HINT_RE_EVAL;" );
3355+ $initpm -> add(" PL_hints &= ~HINT_RE_EVAL;" );
33393356 }
33403357 }
33413358 if ($] < 5.017006) {
0 commit comments