diff options
author | David Mitchell <davem@iabyn.com> | 2017-07-14 11:27:28 +0100 |
---|---|---|
committer | David Mitchell <davem@iabyn.com> | 2017-07-27 11:30:23 +0100 |
commit | 5febd2ff83ad8541c2fd1f43266e321d057ef865 (patch) | |
tree | e827e0dedfac367961b80c6a2d1c8fe34db8fc11 /pp.c | |
parent | f446eca7ef7f31dd356f4dba9401fc3326be139c (diff) | |
download | perl-5febd2ff83ad8541c2fd1f43266e321d057ef865.tar.gz |
pp_length: code tidy and simplify assert
The STATIC_ASSERT_STMT() is basically checking that shifting the
HINT_BYTES byte left 26 places gives you SVf_UTF8, so just assert that.
There's no need to assert the current values of HINT_BYTES and SVf_UTF8.
Other than that, this commit tides up the code a bit (only whitespace
changes and unnecessary brace removal), and adds/updates some code comments.
Diffstat (limited to 'pp.c')
-rw-r--r-- | pp.c | 41 |
1 files changed, 26 insertions, 15 deletions
@@ -3230,22 +3230,29 @@ PP(pp_oct) /* String stuff. */ + PP(pp_length) { dSP; dTARGET; SV * const sv = TOPs; U32 in_bytes = IN_BYTES; - /* simplest case shortcut */ - /* turn off SVf_UTF8 in tmp flags if HINT_BYTES on*/ + /* Simplest case shortcut: + * set svflags to just the SVf_POK|SVs_GMG|SVf_UTF8 from the SV, + * with the SVf_UTF8 flag inverted if under 'use bytes' (HINT_BYTES + * set) + */ U32 svflags = (SvFLAGS(sv) ^ (in_bytes << 26)) & (SVf_POK|SVs_GMG|SVf_UTF8); - STATIC_ASSERT_STMT(HINT_BYTES == 0x00000008 && SVf_UTF8 == 0x20000000 && (SVf_UTF8 == HINT_BYTES << 26)); + + STATIC_ASSERT_STMT(SVf_UTF8 == (HINT_BYTES << 26)); SETs(TARG); - if(LIKELY(svflags == SVf_POK)) + if (LIKELY(svflags == SVf_POK)) goto simple_pv; - if(svflags & SVs_GMG) + + if (svflags & SVs_GMG) mg_get(sv); + if (SvOK(sv)) { STRLEN len; if (!IN_BYTES) { /* reread to avoid using an C auto/register */ @@ -3253,30 +3260,34 @@ PP(pp_length) goto simple_pv; len = sv_len_utf8_nomg(sv); } - else - { + else { /* unrolled SvPV_nomg_const(sv,len) */ - if(SvPOK_nog(sv)){ - simple_pv: + if (SvPOK_nog(sv)) { + simple_pv: len = SvCUR(sv); - } else { + } + else { (void)sv_2pv_flags(sv, &len, 0|SV_CONST_RETURN); } } TARGi((IV)(len), 1); - } else { + } + else { if (!SvPADTMP(TARG)) { + /* OPpTARGET_MY: targ is var in '$lex = length()' */ sv_set_undef(TARG); SvSETMAGIC(TARG); - } else { /* TARG is on stack at this point and is overwriten by SETs. - This branch is the odd one out, so put TARG by default on - stack earlier to let local SP go out of liveness sooner */ + } + else + /* TARG is on stack at this point and is overwriten by SETs. + * This branch is the odd one out, so put TARG by default on + * stack earlier to let local SP go out of liveness sooner */ SETs(&PL_sv_undef); - } } return NORMAL; /* no putback, SP didn't move in this opcode */ } + /* Returns false if substring is completely outside original string. No length is indicated by len_iv = 0 and len_is_uv = 0. len_is_uv must always be true for an explicit 0. |