| Commit message (Collapse) | Author | Age | Files | Lines |
|
|
|
|
|
| |
These two boolean vars weren't being cloned in new threads, and in
debugging builds were getting set to 0xab, which -fsanitize=undefined
regarded as no suitable value for a boolean.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
clang -fsanitize=undefined is being a bit too clever for its own good
here.
The code looks something like
U8 vhex[VHEX_SIZE];
...
v = vhex + ...;
if (v < vend) ...
The code itself is safe, but ASan detects if you've added a value
greater than the buffer size to vhex and whines.
I've changed it so that the conditional comes first and is done in such
a way that arbitrary values can't be added to vhex.
To reproduce:
printf "%.1000a\n", 1;
gives
sv.c:12327:34: runtime error: index 1000 out of bounds for type 'U8 [17]'
|
|
|
|
|
|
|
|
|
| |
Doing uv = -iv is undefined behaviour if iv happens to be IV_MIN.
This occurs in several places in the perl sources.
These ones were found by visual code inspection rather than
using -fsanitize=undefined, but I've added extra tests so that
-fsanitize could find them now.
|
|
|
|
|
|
|
|
|
|
|
| |
Doing uv = -iv is undefined behaviour if iv happens to be IV_MIN.
This occurs in several places in the perl sources.
Found by -fsanitize=undefined.
Here's a typical message:
sv.c:2864:7: runtime error: negation of -9223372036854775808 cannot be represented in type 'IV' (aka 'long'); cast to an unsigned type to negate this value to itself
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Commit 8c6180a91de91a1194f427fc639694f43a903a78 added a warning message
for when Perl determines that the program's underlying locale just
switched into is poorly supported. At the time it was thought that this
would be an extremely rare occurrence. However, a bug in HP-UX -
B.11.00/64 causes this message to be raised for the "C" locale. A
workaround was done that silenced those. However, before it got fixed,
this message would occur gobs of times executing the test suite. It was
raised even if the script is not locale-aware, so that the underlying
locale was completely irrelevant. There is a good prospect that someone
using an older Asian locale as their default would get this message
inappropriately, even if they don't use locales, or switch to a
supported one before using them.
This commit causes the message to be raised only if it actually is
relevant. When not in the scope of 'use locale', the message is stored,
not raised. Upon the first locale-dependent operation within a bad
locale, the saved message is raised, and the storage cleared. I was
able to do this without adding extra branching to the main-line
non-locale execution code. This was done by adding regnodes which get
jumped to by switch statements, and refactoring some existing C tests so
they exclude non-locale right off the bat.
These changes would have been necessary for another locale warning that
I previously agreed to implement, and which is coming a few commits from
now.
I do not know of any way to add tests in the test suite for this. It is
in fact rare for modern locales to have these issues. The way I tested
this was to temporarily change the C code so that all locales are viewed
as defective, and manually note that the warnings came out where
expected, and only where expected.
I chose not to try to output this warning on any POSIX functions called.
I believe that all that are affected are deprecated or scheduled to be
deprecated anyway. And POSIX is closer to the hardware of the machine.
For convenience, I also don't output the message for some zero-length
pattern matches. If something is going to be matched, the message will
likely very soon be raised anyway.
|
| |
|
|
|
|
|
|
| |
We unroll hv_backreferences_p() in sv_get_backrefs() so the logic is simpler,
(we dont need a **SV for this function), and (hopefully) make it C++ compliant
at the same time.
|
|
|
|
|
|
| |
This reverts commit d49cfb746d789072c374f2403d477feb8017ce89.
Better patch coming.
|
| |
|
|
|
|
|
|
|
|
|
|
|
| |
This encapsulates the logic to extract the backrefs from a weak-referent.
Since sv_get_backrefs() can be used for a similar purposes as hv_backreferences_p()
we no longer need to export the later, and therefore this patch also reverts
ad2f46a793b4ade67d45ac0086ae62f6756c2752.
See perl #123473 for related discussion, and https://github.com/Sereal/Sereal/issues/73
for a practical example of why this API is required.
|
|
|
|
| |
See <20141130160250.GC31019@pjcj.net>. Commit 354b74ae6f broke this.
|
| |
|
|
|
|
| |
There has never been such a macro.
|
|
|
|
|
|
|
|
|
| |
to match the existing convention (OpREFCNT, OpSLAB).
Dave Mitchell asked me to wait until after his multideref work
was merged.
Unfortunately, there are now CPAN modules using OP_SIBLING.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
This op is an optimisation for any series of one or more array or hash
lookups and dereferences, where the key/index is a simple constant or
package/lexical variable. If the first-level lookup is of a simple
array/hash variable or scalar ref, then that is included in the op too.
So all of the following are replaced with a single op:
$h{foo}
$a[$i]
$a[5][$k][$i]
$r->{$k}
local $a[0][$i]
exists $a[$i]{$k}
delete $h{foo}
while these aren't:
$a[0] already handled by OP_AELEMFAST
$a[$x+1] not a simple index
and these are partially replaced:
(expr)->[0]{$k} the bit following (expr) is replaced
$h{foo}[$x+1][0] the first and third lookups are each done with
a multideref op, while the $x+1 expression and
middle lookup are done by existing add, aelem etc
ops.
Up until now, aggregate dereferencing has been very heavyweight in ops; for
example, $r->[0]{$x} is compiled as:
gv[*r] s
rv2sv sKM/DREFAV,1
rv2av[t2] sKR/1
const[IV 0] s
aelem sKM/DREFHV,2
rv2hv sKR/1
gvsv[*x] s
helem vK/2
When executing this, in addition to the actual calls to av_fetch() and
hv_fetch(), there is a lot of overhead of pushing SVs on and off the
stack, and calling lots of little pp() functions from the runops loop
(each with its potential indirect branch miss).
The multideref op avoids that by running all the code in a loop in a
switch statement. It makes use of the new UNOP_AUX type to hold an array
of
typedef union {
PADOFFSET pad_offset;
SV *sv;
IV iv;
UV uv;
} UNOP_AUX_item;
In something like $a[7][$i]{foo}, the GVs or pad offsets for @a and $i are
stored as items in the array, along with a pointer to a const SV holding
'foo', and the UV 7 is stored directly. Along with this, some UVs are used
to store a sequence of actions (several actions are squeezed into a single
UV).
Then the main body of pp_multideref is a big while loop round a switch,
which reads actions and values from the AUX array. The two big branches in
the switch are ones that are affectively unrolled (/DREFAV, rv2av, aelem)
and (/DREFHV, rv2hv, helem) triplets. The other branches are various entry
points that handle retrieving the different types of initial value; for
example 'my %h; $h{foo}' needs to get %h from the pad, while '(expr)->{foo}'
needs to pop expr off the stack.
Note that there is a slight complication with /DEREF; in the example above
of $r->[0]{$x}, the aelem op is actually
aelem sKM/DREFHV,2
which means that the aelem, after having retrieved a (possibly undef)
value from the array, is responsible for autovivifying it into a hash,
ready for the next op. Similarly, the rv2sv that retrieves $r from the
typeglob is responsible for autovivifying it into an AV. This action
of doing the next op's work for it complicates matters somewhat. Within
pp_multideref, the autovivification action is instead included as the
first step of the current action.
In terms of benchmarking with Porting/bench.pl, a simple lexical
$a[$i][$j] shows a reduction of approx 40% in numbers of instructions
executed, while $r->[0][0][0] uses 54% fewer. The speed-up for hash
accesses is relatively more modest, since the actual hash lookup (i.e.
hv_fetch()) is more expensive than an array lookup. A lexical $h{foo}
uses 10% fewer, while $r->{foo}{bar}{baz} uses 34% fewer instructions.
Overall,
bench.pl --tests='/expr::(array|hash)/' ...
gives:
PRE POST
------ ------
Ir 100.00 145.00
Dr 100.00 165.30
Dw 100.00 175.74
COND 100.00 132.02
IND 100.00 171.11
COND_m 100.00 127.65
IND_m 100.00 203.90
with cache misses unchanged at 100%.
In general, the more lookups done, the bigger the proportionate saving.
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
I couldnt understand this code at first glance. Many empty conditional
blocks because of page protection ROing which isn't implemented on Win32,
caused erratic stepping in my debugger with CC optimizations *off*.
-read COWREFCNT only once
-save COWREFCNT to an auto for debugger visual inspection
-don't check len twice
-don't write sv_buf_to_rw() twice
No change in behavior is expected.
|
|
|
|
|
|
|
|
| |
Several SAVEt_* types were giving the SVs the wrong reference counts
in ss_dup, causing child process to lose SVs too soon.
See <https://rt.perl.org/Ticket/Display.html?id=40565#txn-1180404>
and <https://rt.perl.org/Ticket/Display.html?id=40565#txn-1277127>.
|
| |
|
| |
|
|
|
|
|
|
| |
op/fork.t test 6 that contains "@a = (1..3);" will crash on Win32 with
special debugging heap and race condition rarely crash otherwise.
Refcnt mistake is from commit ff2a62e0c8 . See perl #40565 for details.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Dave's cachegrind benchmark says "small win":
REF THIS
------ ------
Ir 105.35 105.91
Dr 104.45 105.42
Dw 105.42 105.17
COND 104.33 104.58
IND 107.04 106.76
COND_m 98.55 110.11
IND_m 110.09 111.08
|
| |
|
|
|
|
|
|
|
|
|
|
|
| |
distinct from SV. This should fix the CPAN modules that were failing
when the PadnameLVALUE flag was added, because it shared the same
bit as SVs_OBJECT and pad names were going through code paths not
designed to handle pad names.
Unfortunately, it will probably break other CPAN modules, but I think
this change is for the better, as it makes both pad names and SVs sim-
pler and makes pad names take less memory.
|
|
|
|
| |
This is in preparation for making PADNAME a separate type.
|
|
|
|
| |
Cf. bd30fe8921c88e4677c2279b442a56a11ae037b4 for details.
|
|
|
|
|
| |
Pretty much the same change as
bd30fe8921c88e4677c2279b442a56a11ae037b4 was for newSViv.
|
| |
|
|
|
|
| |
(hpux 10.20 has no quad, and its long double is non-standard)
|
| |
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
newSViv() is not used a whole lot by the core. But it is frequently
used in XS modules. In a nutshell, it allocates a new EMPTY SV just to
call sv_setiv which calls sv_upgrade which in turn spends inordinate
amounts of time looking at the properties of the SV to make it an
SVt_IV. But the properties of that SV are always the same: a clean
slate! Therefore, inlining the very simple bits of sv_setiv that are
actually necessary gives a very tangible speed-up.
It's not very easy to benchmark with with a language-level one-liner
because newSViv() isn't too common in the core. Thus follow XS
micro-benchmarks:
Benchmark 1: Virtually no-op XS function.
SV *
echo_integer(int in)
CODE:
RETVAL = newSViv(in);
OUTPUT: RETVAL
$ dumbbench -i50 --pin-frequency -- ./perl -Ilib \
-MXS::APItest -e 'XS::APItest::echo_integer($_) for 1..1000000'
Before: 3.2782e-01 seconds
After: 3.0530e-01 seconds
A small change, but considering the massive overhead of a function call,
quite surprisingly noticeable.
Benchmark 2: XS function that constructs multiple integer values.
SV *
echo_integer_array(int in)
PREINIT:
int i;
AV *av;
CODE:
av = newAV();
RETVAL = newRV_noinc((SV *)av);
av_extend(av, in-1);
for (i = 0; i < in; ++i)
av_store(av, i, newSViv(i));
OUTPUT: RETVAL
$ dumbbench -i50 --pin-frequency -- ./perl -Ilib \
-MXS::APItest -e 'XS::APItest::echo_integer_array(100) for 1..10000'
Before: 1.18363e-01 seconds
After: 0.92050e-01 seconds
While in the grand scheme of things, this might seem like a very small
optimization, there are many XS modules that actually generate a lot of
integer values, de-serializers being good examples.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
This change simply avoids calling sv_upgrade (which will do a ton of
work to determine source and destination types) in a hot code path where
at that very location, we've already just done all the same leg work to
figure out source and destination types of the SV type conversion. In
this particularly common and simple variant (SVt_NULL to SVt_IV), it's
easy to do much better than sv_upgrade.
Micro-benchmark used to validate this:
$ dumbbench -i50 --pin-frequency -- \
./perl -Ilib -e 'for my $x (1..1000){my @a = (1..2000);}'
Before:
Rounded run time per iteration: 2.4311e-01 +/- 1.4e-04 (0.1%)
After:
Rounded run time per iteration: 1.99354e-01 +/- 5.5e-05 (0.0%)
That's 18% faster. While the micro-benchmark is very heavy on exercising
this code path, it's a common code path. This is expected to have some
real-world impact. There are likely more, similar optimizations that
could have similar impact.
NB: A similar change to newSViv also speeds up newSViv significantly,
but newSViv is hardly used in the core. On the other hand, XS modules
exercise it a lot. The Sereal decoder would be significantly, positively
affected by doing a similar change there.
|
|
|
|
|
|
| |
This commit adds documentation of the bodyless-IV/NV hacks as well as
moving the offset calculation into a somewhat sensibly-named define
instead of cargo-culting the obscure logic in many different places.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
The encoding pragma is deprecated, but in the meantime it causes spooky
action at a distance with other modules that it may be combined with.
In these modules, operations such as chr(), ord(), and utf8::upgrade()
will suddenly start doing the wrong thing.
The documentation for 'encoding' has said to call it after loading other
modules, but this may be impractical. This is especially bad with
anything that auto-loads at first use, like \N{} does now for charnames.
There is an issue with combining this with setting the variable
${^ENCODING} directly. The potential for conflicts has always been
there, and remains. This commit introduces a shadow hidden variable,
subservient to ${^ENCODING} (to preserve backwards compatibility) that
has lexical scope validity.
The pod for 'encoding' has been revamped to be more concise, clear, use
more idiomatic English, and to speak from a modern perspective.
|
|
|
|
|
|
| |
This is in preparation for making the retrieval more complex in future
commits than it is now. This is going into mg.c because the value is
magical.
|
|
|
|
| |
This is in preparation for making the test more complicated.
|
|
|
|
|
| |
This will be used to record whether a pad entry is used as an lvalue
multiple times. If so, it cannot be used as a constant.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
- this improves the error message on ABI incompatibility, per
[perl #123136]
- reduce the number of gv_fetchfile calls in newXS over registering many
XSUBs
- "v" was not stripped from PERL_API_VERSION_STRING since string
"vX.XX.X\0", a typical version number is 8 bytes long, and aligned to
4/8 by most compilers in an image. A double digit maint release is
extremely unlikely.
- newXS_deffile saves on machine code in bootstrap functions by not passing
arg filename
- move newXS to where the rest of the newXS*()s live
- move the "no address" panic closer to the start to get it out of the way
sooner flow wise (it nothing to do with var gv or cv)
- move CvANON_on to not check var name twice
- change die message to use %p, more efficient on 32 ptr/64 IV platforms
see ML post "about commit "util.c: fix comiler warnings""
- vars cv/xs_spp (stack pointer pointer)/xs_interp exist for inspection by
a C debugger in an unoptimized build
|
| |
|
|
|
|
| |
This makes the machine code smaller.
|
|
|
|
|
|
|
|
|
| |
m//, s/// and y/// already have logic to deal with implicit lexical
$_. The pad offset of $_ is stored in the match op itself. We can
take advantage of that and extend it to lexical variables in general.
That way we have fewer ops to execute, as $lex =~ // no longer calls
pp_padsv. It also allows lexical variables’ names to be mentioned in
uninitialized warnings for y///.
|
| |
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
This API elevates the amount of ABI compatibility protection between XS
modules and the interp. It also makes each boot XSUB smaller in machine
code by removing function calls and factoring out code into the new
Perl_xs_handshake and Perl_xs_epilog functions.
sv.c :
- revise padlist duping code to reduce code bloat/asserts on DEBUGGING
ext/DynaLoader/dlutils.c :
- disable version checking so interp startup is faster, ABI mismatches are
impossible because DynaLoader is never available as a shared library
ext/XS-APItest/XSUB-redefined-macros.xs :
- "" means dont check the version, so switch to " " to make the test in
xsub_h.t pass, see ML thread "XS_APIVERSION_BOOTCHECK and XS_VERSION
is CPP defined but "", mow what?"
ext/re/re.xs :
- disable API version checking until #123007 is resolved
ParseXS/Utilities.pm :
109-standard_XS_defs.t :
- remove context from S_croak_xs_usage similar to core commit cb077ed296 .
CvGV doesn't need a context until 5.21.4 and commit ae77754ae2 and
by then core's croak_xs_uage API has been long available and this
backport doesn't need to account for newer perls
- fix test where lack of having PERL_IMPLICIT_CONTEXT caused it to fail
|
|
|
|
|
| |
Commit 0e42d607f5 made PL_apiversion unused. Remove it to save memory in
interp struct.
|
| |
|
|
|
|
| |
Or awake, come to think of it.
|
| |
|
| |
|
| |
|