@@ -4694,40 +4694,91 @@ Perl_newASSIGNOP_maybe_const(pTHX_ OP *left, I32 optype, OP *right)
46944694 left = OpSIBLING(attr);
46954695 OpMORESIB_set(left, NULL);
46964696 OpMORESIB_set(attr, NULL);
4697- /* constany folding should probably be deferred to ck_pad or ck_[sa]assign,
4698- to get proper lhs values. */
4699- if (IS_PADxV_OP(left) && left->op_targ) {
4700- if (IS_CONST_OP(right) && left->op_private == OPpLVAL_INTRO) {
4697+ /* Should constany folding be deferred to ck_[sa]assign? */
4698+ if (IS_PADxV_OP(left) && left->op_targ && left->op_private == OPpLVAL_INTRO) {
4699+ if (IS_CONST_OP(right)) {
47014700 SV* lsv = PAD_SV(left->op_targ);
47024701 SV *rsv = cSVOPx_sv(right);
47034702 if (SvTYPE(lsv) == SVt_NULL || SvTYPE(lsv) == SvTYPE(rsv)) {
4704- DEBUG_k(Perl_deb(aTHX_ "constant fold my %s = %s\n",
4705- SvPEEK(lsv ), SvPEEK(rsv)));
4706- SvSetMagicSV(lsv, rsv);
4703+ DEBUG_k(Perl_deb(aTHX_ "my %s :const = %s\n",
4704+ PAD_COMPNAME_PV(left->op_targ ), SvPEEK(rsv)));
4705+ SvSetMagicSV(lsv, SvREFCNT_inc_NN( rsv) );
47074706 left->op_private = 0; /* rm LVINTRO */
47084707 SvREADONLY_on(lsv);
4708+ op_free(right);
4709+ return ck_pad(left);
4710+ } else if (SvTYPE(lsv) == SVt_PVAV) {
4711+ DEBUG_k(Perl_deb(aTHX_ "my %s[1] :const = (%s)\n",
4712+ PAD_COMPNAME_PV(left->op_targ), SvPEEK(rsv)));
4713+ AvSHAPED_on((AV*)lsv); /* XXX we can even type it */
4714+ av_store((AV*)lsv,0,SvREFCNT_inc_NN(rsv));
4715+ SvREADONLY_on(lsv);
4716+ op_free(right);
4717+ return ck_pad(left);
4718+ }
4719+ }
4720+ else if (IS_TYPE(left, PADAV) && IS_TYPE(right, LIST)) {
4721+ SSize_t i;
4722+ AV* lsv = (AV*)PAD_SV(left->op_targ);
4723+ /* check if all rhs elements are const */
4724+ OP *o = OpSIBLING(OpFIRST(right));
4725+ for (;o && IS_CONST_OP(o); o=OpSIBLING(o)) ;
4726+ if (!o) {
4727+ DEBUG_k(Perl_deb(aTHX_ "my %s[1] :const = (...)\n",
4728+ PAD_COMPNAME_PV(left->op_targ)));
4729+ for (i=0,o=OpSIBLING(OpFIRST(right)); o; o=OpSIBLING(o), i++) {
4730+ SV* rsv = cSVOPx_sv(o); /* XXX check for unique types */
4731+ av_store(lsv, i, SvREFCNT_inc_NN(rsv));
4732+ }
4733+ AvSHAPED_on(lsv); /* we can even type it */
4734+ SvREADONLY_on(lsv);
4735+ op_free(right);
47094736 return ck_pad(left);
47104737 }
47114738 }
47124739 }
4713- /* our, but still a NULL sv */
4714- else if (IS_RV2ANY_OP (left) && IS_CONST_OP(right)) {
4740+ /* our, but still mostly a NULL sv */
4741+ else if (IS_TYPE (left, RV2SV ) && IS_CONST_OP(right)) {
47154742 GV* gv = cGVOPx_gv(OpFIRST(left));
47164743 SV *rsv = cSVOPx_sv(right);
4717- SV* lsv;
4744+ SV * lsv = GvSV(gv) ;
47184745 assert(IS_TYPE(OpFIRST(left), GV));
4719- if (IS_TYPE(left, RV2SV))
4720- lsv = GvSV(gv);
4721- else if (IS_TYPE(left, RV2AV))
4722- lsv = (SV*)GvAV(gv);
4723- else if (IS_TYPE(left, RV2HV))
4724- lsv = (SV*)GvHV(gv);
47254746 if (SvTYPE(lsv) == SVt_NULL || SvTYPE(lsv) == SvTYPE(rsv)) {
4726- DEBUG_k(Perl_deb(aTHX_ "constant fold: our %s = %s\n",
4747+ DEBUG_k(Perl_deb(aTHX_ "our $%s :const = %s\n",
47274748 SvPEEK(lsv), SvPEEK(rsv)));
4728- SvSetMagicSV(lsv, rsv);
4749+ SvSetMagicSV(lsv, SvREFCNT_inc_NN(rsv));
4750+ SvREADONLY_on(lsv);
4751+ return ck_rvconst(left);
4752+ }
4753+ } else if (IS_TYPE(left, RV2AV)) {
4754+ GV* gv = cGVOPx_gv(OpFIRST(left));
4755+ AV *lsv = GvAV(gv);
4756+ /* check if all rhs elements are const */
4757+ if (IS_CONST_OP(right)) {
4758+ SV *rsv = cSVOPx_sv(right);
4759+ DEBUG_k(Perl_deb(aTHX_ "our @%s[1] :const = %s\n",
4760+ SvPEEK((SV*)lsv), SvPEEK(rsv)));
4761+ AvSHAPED_on(lsv); /* we can even type it */
4762+ av_store(lsv, 0, SvREFCNT_inc_NN(rsv));
47294763 SvREADONLY_on(lsv);
4764+ op_free(right);
47304765 return ck_rvconst(left);
4766+ } else if (IS_TYPE(right, LIST)) {
4767+ SSize_t i;
4768+ OP *o = OpSIBLING(OpFIRST(right));
4769+ for (;o && IS_CONST_OP(o); o=OpSIBLING(o)) ;
4770+ if (!o) {
4771+ DEBUG_k(Perl_deb(aTHX_ "our @%s[1] :const = (...)\n",
4772+ SvPEEK((SV*)lsv)));
4773+ for (i=0,o=OpSIBLING(OpFIRST(right)); o; o=OpSIBLING(o), i++) {
4774+ SV* rsv = cSVOPx_sv(o); /* XXX check for unique types */
4775+ av_store(lsv, i, SvREFCNT_inc_NN(rsv));
4776+ }
4777+ AvSHAPED_on(lsv); /* we can even type it */
4778+ SvREADONLY_on(lsv);
4779+ op_free(right);
4780+ return ck_rvconst(left);
4781+ }
47314782 }
47324783 }
47334784 /* else not constant foldable. like a lhs ref or list. */
@@ -4779,13 +4830,15 @@ S_my_kid(pTHX_ OP *o, OP *attrs, OP **imopsp)
47794830 } else if (attrs) {
47804831 GV * const gv = cGVOPx_gv(OpFIRST(o));
47814832 HV *stash = GvSTASH(gv);
4782- int num_const;
47834833 if (!stash) stash = (HV*)SV_NO;
47844834 assert(PL_parser);
47854835 PL_parser->in_my = FALSE;
47864836 PL_parser->in_my_stash = NULL;
4787- num_const = attrs_has_const(attrs, FALSE);
4788- if (num_const)
4837+ /* We cannot get away without loading attributes.pm
4838+ because our $a :const = $i still needs run-time init.
4839+ It also simplifies newASSIGNOP_maybe_const().
4840+ */
4841+ if (attrs_has_const(attrs, FALSE))
47894842 apply_attrs_my(stash, o, attrs, imopsp);
47904843 else
47914844 apply_attrs(stash,
@@ -4827,8 +4880,7 @@ S_my_kid(pTHX_ OP *o, OP *attrs, OP **imopsp)
48274880 stash = PAD_COMPNAME_TYPE(o->op_targ);
48284881 if (!stash)
48294882 stash = PL_curstash;
4830- if (stash != PL_curstash || attrs_has_const(attrs, FALSE) != 1)
4831- apply_attrs_my(stash, o, attrs, imopsp);
4883+ apply_attrs_my(stash, o, attrs, imopsp);
48324884 }
48334885 o->op_flags |= OPf_MOD;
48344886 o->op_private |= OPpLVAL_INTRO;
0 commit comments