Skip to content

Commit

Permalink
opslabs: be cautious casting psize values
Browse files Browse the repository at this point in the history
I could have assert()ed in the macro, but that would have duplicated
the rounding expression.
  • Loading branch information
tonycoz committed Nov 13, 2023
1 parent 8fb1543 commit e3e0332
Show file tree
Hide file tree
Showing 4 changed files with 16 additions and 4 deletions.
1 change: 1 addition & 0 deletions embed.fnc
Original file line number Diff line number Diff line change
Expand Up @@ -4706,6 +4706,7 @@ RST |bool |scalar_mod_type|NULLOK const OP *o \
|I32 type
RS |OP * |search_const |NN OP *o
S |void |simplify_sort |NN OP *o
Ti |U16 |size_to_psize |size_t size
RS |OP * |too_few_arguments_pv \
|NN OP *o \
|NN const char *name \
Expand Down
1 change: 1 addition & 0 deletions embed.h
Original file line number Diff line number Diff line change
Expand Up @@ -1425,6 +1425,7 @@
# define scalarkids(a) S_scalarkids(aTHX_ a)
# define search_const(a) S_search_const(aTHX_ a)
# define simplify_sort(a) S_simplify_sort(aTHX_ a)
# define size_to_psize S_size_to_psize
# define too_few_arguments_pv(a,b,c) S_too_few_arguments_pv(aTHX_ a,b,c)
# define too_many_arguments_pv(a,b,c) S_too_many_arguments_pv(aTHX_ a,b,c)
# define voidnonfinal(a) S_voidnonfinal(aTHX_ a)
Expand Down
14 changes: 10 additions & 4 deletions op.c
Original file line number Diff line number Diff line change
Expand Up @@ -207,7 +207,13 @@ Perl_op_prune_chain_head(OP** op_p)
#endif

/* rounds up to nearest pointer */
#define SIZE_TO_PSIZE(x) ((U16)(((x) + sizeof(I32 *) - 1)/sizeof(I32 *)))
PERL_STATIC_INLINE U16
S_size_to_psize(size_t sz) {
size_t psize = (sz + sizeof(I32 *) - 1) / sizeof(I32 *);
assert(psize < U16_MAX);

return (U16)psize;
}

#define DIFF(o,p) \
(assert((size_t)((char *)(p) - (char *)(o)) % sizeof(I32**) == 0), \
Expand All @@ -221,7 +227,7 @@ Perl_op_prune_chain_head(OP** op_p)
)

/* opslot_size includes the size of the slot header, and an op can't be smaller than BASEOP */
#define OPSLOT_SIZE_BASE (SIZE_TO_PSIZE(sizeof(OPSLOT)))
#define OPSLOT_SIZE_BASE (size_to_psize(sizeof(OPSLOT)))

/* the number of bytes to allocate for a slab with sz * sizeof(I32 **) space for op */
#define OpSLABSizeBytes(sz) \
Expand Down Expand Up @@ -350,7 +356,7 @@ Perl_Slab_Alloc(pTHX_ size_t sz)
else ++(head_slab = (OPSLAB *)CvSTART(PL_compcv))->opslab_refcnt;

/* size in pointer units, including the OPSLOT header */
U16 sz_in_p = SIZE_TO_PSIZE(sz + OPSLOT_HEADER);
U16 sz_in_p = size_to_psize(sz + OPSLOT_HEADER);

/* The head slab for each CV maintains a free list of OPs. In particular, constant folding
will free up OPs, so it makes sense to re-use them where possible. A
Expand Down Expand Up @@ -9501,7 +9507,7 @@ Perl_newFOROP(pTHX_ I32 flags, OP *sv, OP *expr, OP *block, OP *cont)
* keep it in-place if there's space */
if (loop->op_slabbed
&& OpSLOT(loop)->opslot_size
< SIZE_TO_PSIZE(sizeof(LOOP) + OPSLOT_HEADER))
< size_to_psize(sizeof(LOOP) + OPSLOT_HEADER))
{
/* no space; allocate new op */
LOOP *tmp;
Expand Down
4 changes: 4 additions & 0 deletions proto.h

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

0 comments on commit e3e0332

Please sign in to comment.