SvPV_shrink_to_cur: include space for COW
The SvPV_shrink_to_cur macro shrinks an allocation to SvCUR(sv) + 1, which does not include an additional byte for Copy-On-Write (COW).
GH#22116 - a902d92a78262a0fd111789742f9c9e2a7fa2f42 - short-circuited constant folding on CONST OPs, as this should be unnecessary. However, Dave Mitchell noticed that it had the inadvertent effect of disabling COW on SVs holding UTF8 string literals (e.g. "\x{100}abcd").
When a CONST OP is created, Perl_ck_svconst should mark its SV as being COW-able. But SVs built via S_scan_const, when that has called SvPV_shrink_to_cur, have resulting SvLEN(sv) values that fail the SvCANCOW(sv) test. Previously, constant folding had the effect of copying the literal into a buffer large enough for COW.
This commit modifies SvPV_shrink_to_cur so that it accounts for an additional byte for COW.
Additionally, this macro will no longer try to shrink the buffer below PERL_STRLEN_NEW_MIN, since that is likely to have no effect.
- This set of changes does not require a perldelta entry.
While this change seems sensible in general, it's changing the behaviour of an API macro: which makes me think it's not a suitable candidate for a last-minute change. Would it possible to have a more narrow fix which only affects utf8 literals, then apply the change in the PR after 5.42.0 is released? Apart from that, I can confirm that this PR fixes the issue at hand, and also the performance regression which alerted me to the issue initially.
Would it possible to have a more narrow fix which only affects utf8 literals, then apply the change in the PR after 5.42.0 is released?
Yes, the short circuit check in Perl_op_convert_list can be made to check to see if the CONST OP's SV has IsCOW, which should do it. I'll swap that for an assertion at the start of the next dev cycle.
I've just improved some of the code comments and commit messages, but made no changes to the code. Will let the CI run and then merge later today.