| Commit message (Collapse) | Author | Age | Files | Lines |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Move the assignments to SvFLAGS(sv) after the check for SvOOK(), and use
arena_index for the array index to PL_body_roots. Without both fixes,
del_body() would always be called with &PL_body_roots[SVt_PVHV], which is
wrong if the body was allocated from &PL_body_roots[HVAUX_ARENA_ROOT_IX].
PVHV body handling was changed recently by commit 94ee6ed79dbca73d:
Split the XPVHV body into two variants "normal" and "with aux"
Default to the smaller body, and switch to the larger body if we need to
allocate a C<struct xpvhv_aux> (eg need an iterator).
This restores the previous small size optimisation for hashes used as
objects.
as part of changing where memory for C<struct xpvhv_aux> is allocated.
The new implementation uses two sizes of "bodies" for PVHVs - the default
body is unchanged, but when a hash needs a C<struct xpvhv_aux>, it now
swaps out the default body for a larger body with space for the struct.
(Previously it would reallocate the memory used for HvARRAY() to make space
for the struct there - an approach which requires more tracking of changed
pointers.)
That commit was subtly buggy in that on hash deallocation it didn't *return*
hash bodies to the correct arena. As-was, it would return both sizes of hash
body to the arena for the default (smaller) body. This was due to a
combination of two subtle bugs
1) the explicit reset of all SvFLAGS to SVf_BREAK would implicitly clear
SVf_OOK. That flag bit set is needed to signal the different body size
2) The code must call del_body() with &PL_body_roots[arena_index], not
&PL_body_roots[type]
type is SVt_PVHV for both body sizes. arena_index is SVt_PVHV for the
smaller (default) bodies, and HVAUX_ARENA_ROOT_IX for the larger bodies.
There were no memory errors or leaks (that would have been detectable by
tools such as ASAN or valgrind), but the bug meant that larger hash bodies
would never get re-used. So for code that was steady-state creating and
destroying hashes with iterators (or similar), instead of those bodies being
recycled via their correct arena, the interpreter would need to continuously
allocate new memory for that arena, whilst accumulating ever more unused
"smaller" bodies in the other arena.
I didn't spot this bug whilst reviewing commit 8461dd8ad90b2bce:
don't overwrite the faked up type details for hv-with-aux
CID 340472
which is in the same area of the code, but fixes a related problem.
Curiously when reporting CID 340738:
Assigning value "SVt_IV" to "arena_index" here, but that stored value is
overwritten before it can be used
Coverity also didn't spot that the code in question was unconditionally
unreachable, and warn about that, or modify its warning to note that.
(For the code prior to this commit SvOOK(sv) at that point could only ever
be false. This is obscured thanks to macros, but all these macros are
unconditionally defined to the same values, so static analysis should be
able to infer that they are actually constant, and reason accordingly.
To be fair, this is *hard*. But not impossible. Hence I infer that static
analysis tools still have room for improvement, and can make "mistakes".)
Ironically, defining PURIFY would hide this bug, because that disables the
use of arenas, instead allocating all bodies explicitly with malloc() and
releasing them with free(), and free() doesn't need to know the size of the
memory block, hence it wouldn't matter that the code had that size wrong.
|
| |
|
| |
|
| |
|
|
|
|
| |
CID 340472
|
|
|
|
|
|
|
|
| |
Default to the smaller body, and switch to the larger body if we need to
allocate a C<struct xpvhv_aux> (eg need an iterator).
This restores the previous small size optimisation for hashes used as
objects.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Rename the macro new_body_inline() to new_body_from_arena().
The macro existed to provide an inline implementation for hot code paths,
with a small function for the others. Now that we have proper inline
functions, change the function to be inlined, and use it instead of the
macro. There is no change to the code generated for the hot paths. This
makes the source simpler.
Yes, this will also inline the function in a couple of other places, but
these days optimising compilers often do that anyway for small functions.
Even if they aren't for this function (as was), the size of the function
itself is comparable with the calling overheads, so it's not a massive
penalty.
Two if blocks now need to be placed inside #ifndef PURIFY/#endif guards
because they now use the function S_new_body(), which is not defined with
PURIFY. The code is actually unreachable - defining PURIFY causes all
values for new_type_details->arena to be forced to 0 - hence the if was
never true under PURIFY. Hence it could have been guarded the same way
previously, but for (maybe false) improved readability was not. Previously
there wasn't a compilation failure because the unreachable code was using
a macro, not a static function, and the macro was always defined, even when
not used.
Really the macro's definition should have been inside #ifndef PURIFY, so
fix this oversight - it is now only defined if it is needed.
Retain the macro (with a new name), and split the parameters to the macro.
This will make the next commit simpler.
|
|
|
|
|
| |
These three variables don't hold their values between iterations of the
while loop, so can be declared within it, to make this obvious.
|
|
|
|
|
|
| |
The longer name more accurately reflects what the constant refers to.
Correct the comments describing how some arena roots are re-used.
|
|
|
|
|
| |
For now, memory for this structure is always allocated, even though it
isn't always flagged as being present.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
PVLV scalars are used to implement various obscure features of perl, such as
elements in tied hashes and hash lookups used as function parameters. To
make these work, PVLVs must be capable of holding all scalar types. First
class REGEXPs are larger than PVLVs, hence there is special case code to
attach REGEXP bodies to PVLVs, for code that both dereferences a regex object
and then assigns that value to a PVLV scalar. This was first implemented in
Oct 2012 by commit 8d919b0a35f2b57a:
Allow regexp-to-pvlv assignment
and improved in July 2017 with commit df6b4bd56551f2d3:
It turns out that the implementation would leak a scalar body, for the
"normal" use case (of this obscure feature). This wasn't noticed for two
reasons
1) bodies are allocated from arenas, and arenas are correctly freed during
full destruction.
2) the body is not leaked if the the PVLV scalar is then modified
The regression tests added by commit 8d919b0a35f2b57a were also testing
the corner case of concatenating to one of these values - ie that
sv_force_normal_flags() handled unwinding the special cases correctly.
To avoid code duplication, the tests added by that commit caused all PVLV
scalars to be passed to sv_force_normal_flags(), so didn't actually test
regular destruction of such scalars.
The tests added in Aug 2017 by commit 622c613e12cef84c:
PVLV-as-REGEXP: avoid PVX double free
With v5.27.2-30-gdf6b4bd, I changed the way that PVLVs store a regexp
value (by making the xpv_len field point to a regexp struct). There was a
bug in this, which caused the PVX buffer to be double freed.
Several REGEXP SVs can share a PVX buffer. Only one of them will have a
non-zero xpv_len field, and that SV gets to free the buffer.
After the commit above, the non-zero xpv_len was triggering an extra free.
This was showing up in smokes as failures in re/recompile.t when invoked
with PERL_DESTRUCT_LEVEL=2 (which t/TEST does).
were actually the first to expose this bug, even though it had been present
since 2012.
The bug is only visible with a full leak test (eg valgrind --leak-check=full
or an ASAN build) with -DPURIFY (to disable arenas), hence why it hasn't
been noticed.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
When trying to evaluate:
$x{$y}
or
$x[$y]
where both the index and the hash or array entry was undefined,
when trying to report the entry as uninitialised, find_uninit_var()
would try to get the string or numeric value of the index,
recursively trying to produce a warning.
This would end up overflowing the stack, producing a segmentation fault.
Fixes #19147.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
This is minor a a regression introduced by commit 914bb57489325d34:
Define a third kind of COW state; STATIC
...
sv_setsv_flags() and sv_setsv_cow() will preserve this state
There was a small omission in the copy code - it didn't handle the case where
the destination SV owned a string buffer already. This is actually
relatively rare - triggering it requires a scalar in code path that is
assigned both strings and booleans. Minimal test case is:
my $got = 1;
$got .= "";
$got = ref "";
cut down from &is in t/comp/parser.t
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Previously, when IsCOW flag was set there were two cases:
SvLEN()==0:
PV is really a shared HEK
SvLEN()!=0:
PV is a COW structure with 1..256 refcount stored in its extra final byte
This change adds a third state:
SvLEN()==0 && SvFLAGS() & SVppv_STATIC:
PV is a shared static const pointer and must not be modified
sv_setsv_flags() and sv_setsv_cow() will preserve this state
sv_uncow() will copy it out to a regular string buffer
sv_dup() will preserve the static pointer into cloned threads
|
|
|
|
| |
gcc-11.2 correctly complains about this. [-Wmisleading-indentation]
|
|
|
|
|
| |
This is a better choice for an "is it empty?" optimisation, as HvARRAY()
can be non-NULL even when there actually are no keys.
|
|
|
|
| |
functions
|
| |
|
| |
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Adds syntax `defer { BLOCK }` to create a deferred block; code that is
deferred until the scope exits. This syntax is guarded by
use feature 'defer';
Adds a new opcode, `OP_PUSHDEFER`, which is a LOGOP whose `op_other` field
gives the start of an optree to be deferred until scope exit. That op
pointer will be stored on the save stack and invoked as part of scope
unwind.
Included is support for `B::Deparse` to deparse the optree back into
syntax.
|
|
|
|
|
| |
SvNV_nomg(argsv) is redundant here because its NV is already loaded
to the local variable "nv".
|
| |
|
|
|
|
|
|
|
| |
The print took a character, cast it to UV and then printed it as an
octal UV. But why not just print it as an unsigned octal character?
The code that did this was part of a sweeping commit of a bunch of
things, so no explanation there.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
The code is looping to look for the hash key whose value is the SV at the
address given in val. Previously the code in the loop would ignore hash
entries which were &PL_sv_undef or &PL_sv_placeholder. Given that this check
was *after* the equality check for val, but the the only way for the
function to return success ("found") was to continue beyond this check.
Hence, as-written it meant that the function would always return NULL
("not found") if val had either of these values, but would loop through the
entire hash *first* before doing so.
Hence move the check before the loop, to generate the same result, but with
less work.
Also, HeKEY(entry) can never be NULL, so this check was dead code and can be
removed. (The C compiler probably already spotted this)
Also, the code had special-case handling for HEf_SVKEY. What it used to do
was actually identical to what sv_2mortal(newSVhek(...)) does, so just use
that for everything. (Hashes themselves should never contain keys with this
special flag length - it's only used in MAGIC structures, and for HE
structures created while iterating tied hashes.)
|
|
|
|
| |
http://nntp.perl.org/group/perl.perl5.porters/26082
|
|
|
|
|
|
|
|
|
|
|
|
| |
Since the removal of PERL_OBJECT
(acfe0abcedaf592fb4b9cb69ce3468308ae99d91) PERL_IMPLICIT_CONTEXT and
MULTIPLICITY have been synonymous and they're being used interchangeably.
To simplify the code, this commit replaces all instances of
PERL_IMPLICIT_CONTEXT with MULTIPLICITY.
PERL_IMPLICIT_CONTEXT will stay defined for compatibility with XS
modules.
|
|
|
|
|
|
|
| |
This is a rebasing by @khw of part of GH #18792, which I needed to get
in now to proceed with other commits.
It also strips trailing white space from the affected files.
|
|
|
|
| |
In particular, if the length is beyond the end, it should not be stored as the end.
|
| |
|
|
|
|
|
|
|
|
|
|
|
| |
* Support %#p form of %..p
Fix #18289
* Better testing
* Add myself to AUTHORS
* Add a comment
|
|
|
|
|
|
| |
Observed in clang 9 and 10.
Partial solution for https://github.com/Perl/perl5/issues/17015
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
All of perl's printf() style processing meets up in sv_vcatpvfn_flags()
which had three problems when dealing with long double parameters.
1) both the long double (L and q) and __float128 flags (Q) were
converted to the internal long double flag
2) the internal long double flag was then always treated as a __float128
parameter.
3) the non-Q format string was then passed to my_snprintf(), which
throws an exception on non-Q floating point formats, which meant that
C/XS code printing doubles or long doubles in a quadmath built would
throw an exception.
|
| |
|
| |
|
|
|
|
|
|
|
|
|
|
| |
Every use of it already has its own semicolon, and duplicating it
can lead to warnings like this:
ALIGNED_TYPE(XPVGV);
...................^
%CC-I-EXTRASEMI, Extraneous semicolon.
at line number 894 in file D0:[craig.blead]sv.c;1
|
|
|
|
|
| |
66435b24ea changed Perl_isnan to Perl_isinfnan, but I forgot to update
corresponding preprocessor conditionals.
|
|
|
|
|
| |
This commit will partially revert the effect of the commit
c33ee94ba2086d48e3750cfdeb51402b61bb1ac7. [GH #18388]
|
|
|
|
|
|
|
|
|
| |
Previously, imprecision warnings on increment (Lost precision when
incrementing %f by 1) were only issued on positive finite values,
and, on decrement, only issued on negative finite values.
This commit extends this warnings on both sign and infinite values.
This fixes GH #18333.
|
| |
|
| |
|
| |
|
|
|
|
|
| |
There are documented macros that one is supposed to use instead for this
functionality.
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
This fixes GH #18341
There are problems with getenv() on threaded perls wchich can lead to
incorrect results when compiled with PERL_MEM_LOG.
Commit 0b83dfe6dd9b0bda197566adec923f16b9a693cd fixed this for some
platforms, but as Tony Cook, pointed out there may be
standards-compliant platforms that that didn't fix.
The detailed comments outline the issues and (complicated) full solution.
|
| |
|
|
|
|
|
|
|
| |
Most uses of SAVEt_STRLEN actually store small values; often zero.
Rather than using an entire U64-sized element for these values, it saves
space to use the same "SMALL" mechanism as other numerical values, like
SAVEt_INT_SMALL.
|
|
|
|
| |
5.32 did this for one form; now all do.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
These were occurring on FreeBSD smokes.
warning: implicit conversion from 'IV' (aka 'long') to 'double' changes value from 9223372036854775807 to 9223372036854775808 [-Wimplicit-int-float-conversion]
9223372036854775807 is IV_MAX. What needed to be done here was to use
the NV containing IV_MAX+1, a value that already exists in perl.h
In other instances, simply casting to an NV before doing the comparison
with the NV was what was needed.
This fixes #18328
|