summaryrefslogtreecommitdiff
path: root/pp_ctl.c
diff options
context:
space:
mode:
authorFather Chrysostomos <sprout@cpan.org>2014-01-10 05:59:39 -0800
committerFather Chrysostomos <sprout@cpan.org>2014-01-10 21:29:07 -0800
commit6567ce247355a30b24897ffb2fc9bb1ed73c55f5 (patch)
tree55229842b02b3b986a8b1a80bc54bb07a47e2ef0 /pp_ctl.c
parentbbc1b4cdea1c1cb2ee606d18f791bc97214123e1 (diff)
downloadperl-6567ce247355a30b24897ffb2fc9bb1ed73c55f5.tar.gz
Fix require’s get-magic handling for @INC elements
It was only calling get-magic before checking whether the argument was a reference if the array was tied, which is not the only thing that can cause an @INC element to have get-magic. It should have been checking for get-magic on the element itself (which is a faster check, too). And then there were too many FETCH calls. I do not know whether we should be calling get-magic exactly once when the ‘Can’t locate’ error occurs. At least this commit reduces the number of FETCHes.
Diffstat (limited to 'pp_ctl.c')
-rw-r--r--pp_ctl.c13
1 files changed, 9 insertions, 4 deletions
diff --git a/pp_ctl.c b/pp_ctl.c
index d47e983d56..fcfa3a15bc 100644
--- a/pp_ctl.c
+++ b/pp_ctl.c
@@ -3815,17 +3815,17 @@ PP(pp_require)
for (i = 0; i <= AvFILL(ar); i++) {
SV * const dirsv = *av_fetch(ar, i, TRUE);
- if (SvTIED_mg((const SV *)ar, PERL_MAGIC_tied))
- mg_get(dirsv);
+ SvGETMAGIC(dirsv);
if (SvROK(dirsv)) {
int count;
SV **svp;
SV *loader = dirsv;
if (SvTYPE(SvRV(loader)) == SVt_PVAV
- && !sv_isobject(loader))
+ && !SvOBJECT(SvRV(loader)))
{
loader = *av_fetch(MUTABLE_AV(SvRV(loader)), 0, TRUE);
+ SvGETMAGIC(loader);
}
Perl_sv_setpvf(aTHX_ namesv, "/loader/0x%"UVxf"/%s",
@@ -3846,6 +3846,11 @@ PP(pp_require)
PUSHs(dirsv);
PUSHs(nsv);
PUTBACK;
+ if (SvGMAGICAL(loader)) {
+ SV *l = sv_newmortal();
+ sv_setsv_nomg(l, loader);
+ loader = l;
+ }
if (sv_isobject(loader))
count = call_method("INC", G_ARRAY);
else
@@ -3946,7 +3951,7 @@ PP(pp_require)
STRLEN dirlen;
if (SvOK(dirsv)) {
- dir = SvPV_const(dirsv, dirlen);
+ dir = SvPV_nomg_const(dirsv, dirlen);
} else {
dir = "";
dirlen = 0;