Skip to content

Commit 8808c6a

Browse files
committed
op.c: factor out repeated entersub code
... for locating the beginning of the argument list and the end (which is the entered sub itself) in the op tree.
1 parent 8166f2f commit 8808c6a

File tree

1 file changed

+39
-27
lines changed

1 file changed

+39
-27
lines changed

op.c

Lines changed: 39 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -9652,6 +9652,33 @@ Perl_newWHILEOP(pTHX_ I32 flags, I32 debuggable, LOOP *loop,
96529652
return o;
96539653
}
96549654

9655+
#define find_argop_from_entersub(op) S_find_argop_from_entersub(aTHX_ op)
9656+
static OP *
9657+
S_find_argop_from_entersub(pTHX_ OP *entersubop) {
9658+
assert(entersubop != NULL);
9659+
9660+
OP *aop = cUNOPx(entersubop)->op_first;
9661+
if (!OpHAS_SIBLING(aop)) {
9662+
aop = cUNOPx(aop)->op_first;
9663+
}
9664+
/* move past pushmark */
9665+
aop = OpSIBLING(aop);
9666+
9667+
return aop;
9668+
}
9669+
9670+
#define find_cvop_from_argop(op) S_find_cvop_from_argop(aTHX_ op)
9671+
static OP *
9672+
S_find_cvop_from_argop(pTHX_ OP *cvop) {
9673+
assert(cvop != NULL);
9674+
9675+
/* CV is the last argument to entersub */
9676+
while (OpHAS_SIBLING(cvop)) {
9677+
cvop = OpSIBLING(cvop);
9678+
}
9679+
return cvop;
9680+
}
9681+
96559682
#define op_is_cv_xsub(o, xsub) S_op_is_cv_xsub(aTHX_ o, xsub)
96569683
static bool
96579684
S_op_is_cv_xsub(pTHX_ OP *o, XSUBADDR_t xsub)
@@ -9693,13 +9720,8 @@ S_op_is_call_to_cv_xsub(pTHX_ OP *o, XSUBADDR_t xsub)
96939720
return false;
96949721

96959722
/* entersub may be a UNOP, not a LISTOP, so we can't just use op_last */
9696-
OP *aop = cUNOPo->op_first;
9697-
if (!OpHAS_SIBLING(aop)) {
9698-
aop = cUNOPx(aop)->op_first;
9699-
}
9700-
aop = OpSIBLING(aop);
9701-
OP *cvop;
9702-
for (cvop = aop; OpHAS_SIBLING(cvop); cvop = OpSIBLING(cvop)) ;
9723+
OP *aop = find_argop_from_entersub(o);
9724+
OP *cvop = find_cvop_from_argop(aop);
97039725

97049726
return op_is_cv_xsub(cvop, xsub);
97059727
}
@@ -14723,10 +14745,7 @@ Perl_ck_entersub_args_list(pTHX_ OP *entersubop)
1472314745

1472414746
PERL_ARGS_ASSERT_CK_ENTERSUB_ARGS_LIST;
1472514747

14726-
aop = cUNOPx(entersubop)->op_first;
14727-
if (!OpHAS_SIBLING(aop))
14728-
aop = cUNOPx(aop)->op_first;
14729-
for (aop = OpSIBLING(aop); OpHAS_SIBLING(aop); aop = OpSIBLING(aop)) {
14748+
for (aop = find_argop_from_entersub(entersubop); OpHAS_SIBLING(aop); aop = OpSIBLING(aop)) {
1473014749
/* skip the extra attributes->import() call implicitly added in
1473114750
* something like foo(my $x : bar)
1473214751
*/
@@ -14773,7 +14792,7 @@ Perl_ck_entersub_args_proto(pTHX_ OP *entersubop, GV *namegv, SV *protosv)
1477314792
{
1477414793
STRLEN proto_len;
1477514794
const char *proto, *proto_end;
14776-
OP *aop, *prev, *cvop, *parent;
14795+
OP *aop, *prev, *parent;
1477714796
int optional = 0;
1477814797
I32 arg = 0;
1477914798
I32 contextclass = 0;
@@ -14795,7 +14814,7 @@ Perl_ck_entersub_args_proto(pTHX_ OP *entersubop, GV *namegv, SV *protosv)
1479514814
}
1479614815
prev = aop;
1479714816
aop = OpSIBLING(aop);
14798-
for (cvop = aop; OpHAS_SIBLING(cvop); cvop = OpSIBLING(cvop)) ;
14817+
OP *cvop = find_cvop_from_argop(aop);
1479914818
while (aop != cvop) {
1480014819
OP* o3 = aop;
1480114820

@@ -15030,18 +15049,17 @@ Perl_ck_entersub_args_proto_or_list(pTHX_ OP *entersubop,
1503015049
OP *
1503115050
Perl_ck_entersub_args_core(pTHX_ OP *entersubop, GV *namegv, SV *protosv)
1503215051
{
15052+
PERL_ARGS_ASSERT_CK_ENTERSUB_ARGS_CORE;
15053+
1503315054
IV cvflags = SvIVX(protosv);
1503415055
int opnum = cvflags & 0xffff;
1503515056
OP *aop = cUNOPx(entersubop)->op_first;
1503615057

15037-
PERL_ARGS_ASSERT_CK_ENTERSUB_ARGS_CORE;
15038-
1503915058
if (!opnum) {
15040-
OP *cvop;
1504115059
if (!OpHAS_SIBLING(aop))
1504215060
aop = cUNOPx(aop)->op_first;
1504315061
aop = OpSIBLING(aop);
15044-
for (cvop = aop; OpSIBLING(cvop); cvop = OpSIBLING(cvop)) ;
15062+
OP *cvop = find_cvop_from_argop(aop);
1504515063
if (aop != cvop) {
1504615064
SV *namesv = cv_name((CV *)namegv, NULL, CV_NAME_NOTQUAL);
1504715065
yyerror_pv(form("Too many arguments for %" SVf,
@@ -15319,21 +15337,15 @@ S_entersub_alloc_targ(pTHX_ OP * const o)
1531915337
OP *
1532015338
Perl_ck_subr(pTHX_ OP *o)
1532115339
{
15322-
OP *aop, *cvop;
15323-
CV *cv;
15324-
GV *namegv;
1532515340
SV **const_class = NULL;
1532615341
OP *const_op = NULL;
1532715342

1532815343
PERL_ARGS_ASSERT_CK_SUBR;
1532915344

15330-
aop = cUNOPx(o)->op_first;
15331-
if (!OpHAS_SIBLING(aop))
15332-
aop = cUNOPx(aop)->op_first;
15333-
aop = OpSIBLING(aop);
15334-
for (cvop = aop; OpHAS_SIBLING(cvop); cvop = OpSIBLING(cvop)) ;
15335-
cv = rv2cv_op_cv(cvop, RV2CVOPCV_MARK_EARLY);
15336-
namegv = cv ? (GV*)rv2cv_op_cv(cvop, RV2CVOPCV_MAYBE_NAME_GV) : NULL;
15345+
OP *aop = find_argop_from_entersub(o);
15346+
OP *cvop = find_cvop_from_argop(aop);
15347+
CV *cv = rv2cv_op_cv(cvop, RV2CVOPCV_MARK_EARLY);
15348+
GV *namegv = cv ? (GV*)rv2cv_op_cv(cvop, RV2CVOPCV_MAYBE_NAME_GV) : NULL;
1533715349

1533815350
o->op_private &= ~1;
1533915351
o->op_private |= (PL_hints & HINT_STRICT_REFS);

0 commit comments

Comments
 (0)