diff options
author | Father Chrysostomos <sprout@cpan.org> | 2010-10-04 12:24:37 -0700 |
---|---|---|
committer | Father Chrysostomos <sprout@cpan.org> | 2010-10-04 12:24:37 -0700 |
commit | b20c4ee1fc23699f6cbe3ce96cc8fe6eb4c52c4c (patch) | |
tree | eca209c69315093bfbc071361e1898bf6a1b109e /pp.c | |
parent | 1ccd2973f698bfdb82dfadf6ef09ec337061a97f (diff) | |
download | perl-b20c4ee1fc23699f6cbe3ce96cc8fe6eb4c52c4c.tar.gz |
[perl #20661] Constant strings representing a number can BECOME numbers
The & | ^ operators now avoid turning on numericness of read-only
arguments.
Diffstat (limited to 'pp.c')
-rw-r--r-- | pp.c | 8 |
1 files changed, 8 insertions, 0 deletions
@@ -2386,6 +2386,8 @@ PP(pp_bit_and) { dPOPTOPssrl; if (SvNIOKp(left) || SvNIOKp(right)) { + const bool left_ro_nonnum = !SvNIOKp(left) && SvREADONLY(left); + const bool right_ro_nonnum = !SvNIOKp(right) && SvREADONLY(right); if (PL_op->op_private & HINT_INTEGER) { const IV i = SvIV_nomg(left) & SvIV_nomg(right); SETi(i); @@ -2394,6 +2396,8 @@ PP(pp_bit_and) const UV u = SvUV_nomg(left) & SvUV_nomg(right); SETu(u); } + if (left_ro_nonnum) SvNIOK_off(left); + if (right_ro_nonnum) SvNIOK_off(right); } else { do_vop(PL_op->op_type, TARG, left, right); @@ -2412,6 +2416,8 @@ PP(pp_bit_or) { dPOPTOPssrl; if (SvNIOKp(left) || SvNIOKp(right)) { + const bool left_ro_nonnum = !SvNIOKp(left) && SvREADONLY(left); + const bool right_ro_nonnum = !SvNIOKp(right) && SvREADONLY(right); if (PL_op->op_private & HINT_INTEGER) { const IV l = (USE_LEFT(left) ? SvIV_nomg(left) : 0); const IV r = SvIV_nomg(right); @@ -2424,6 +2430,8 @@ PP(pp_bit_or) const UV result = op_type == OP_BIT_OR ? (l | r) : (l ^ r); SETu(result); } + if (left_ro_nonnum) SvNIOK_off(left); + if (right_ro_nonnum) SvNIOK_off(right); } else { do_vop(op_type, TARG, left, right); |