Skip to content

Commit 7a5fd60

Browse files
committed
Stage 1 of utf8 support for soft references.
Change gv_fetchpv to take a UTF8 flag, as gv_fetchpvn_flags Add gv_fetchsv to look up a GV by SV rather than a char * pointer Provide a backwards compatability gv_fetchpv Migrate from gv_fetchpv to gv_fetchsv where the caller was grabbing the pointer from an SV All tests still pass. p4raw-id: //depot/perl@23766
1 parent 92ca981 commit 7a5fd60

16 files changed

+130
-93
lines changed

embed.fnc

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1486,4 +1486,8 @@ np |long |my_betohl |long n
14861486

14871487
np |void |my_swabn |void* ptr|int n
14881488

1489+
Ap |GV* |gv_fetchpvn_flags|const char* name|STRLEN len|I32 flags|I32 sv_type
1490+
Ap |GV* |gv_fetchsv|SV *name|I32 flags|I32 sv_type
1491+
dp |bool |is_gv_magical_sv|SV *name|U32 flags
1492+
14891493
END_EXTERN_C

embed.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2278,6 +2278,11 @@
22782278
#ifdef PERL_CORE
22792279
#define my_swabn Perl_my_swabn
22802280
#endif
2281+
#define gv_fetchpvn_flags Perl_gv_fetchpvn_flags
2282+
#define gv_fetchsv Perl_gv_fetchsv
2283+
#ifdef PERL_CORE
2284+
#define is_gv_magical_sv Perl_is_gv_magical_sv
2285+
#endif
22812286
#define ck_anoncode Perl_ck_anoncode
22822287
#define ck_bitop Perl_ck_bitop
22832288
#define ck_concat Perl_ck_concat
@@ -4893,6 +4898,11 @@
48934898
#ifdef PERL_CORE
48944899
#define my_swabn Perl_my_swabn
48954900
#endif
4901+
#define gv_fetchpvn_flags(a,b,c,d) Perl_gv_fetchpvn_flags(aTHX_ a,b,c,d)
4902+
#define gv_fetchsv(a,b,c) Perl_gv_fetchsv(aTHX_ a,b,c)
4903+
#ifdef PERL_CORE
4904+
#define is_gv_magical_sv(a,b) Perl_is_gv_magical_sv(aTHX_ a,b)
4905+
#endif
48964906
#define ck_anoncode(a) Perl_ck_anoncode(aTHX_ a)
48974907
#define ck_bitop(a) Perl_ck_bitop(aTHX_ a)
48984908
#define ck_concat(a) Perl_ck_concat(aTHX_ a)

global.sym

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -673,3 +673,5 @@ Perl_save_set_svflags
673673
Perl_hv_assert
674674
Perl_hv_clear_placeholders
675675
Perl_hv_scalar
676+
Perl_gv_fetchpvn_flags
677+
Perl_gv_fetchsv

gv.c

Lines changed: 33 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -650,14 +650,30 @@ Perl_gv_stashsv(pTHX_ SV *sv, I32 create)
650650

651651

652652
GV *
653-
Perl_gv_fetchpv(pTHX_ const char *nambeg, I32 add, I32 sv_type)
653+
Perl_gv_fetchpv(pTHX_ const char *nambeg, I32 add, I32 sv_type) {
654+
STRLEN len = strlen (nambeg);
655+
return gv_fetchpvn_flags(nambeg, len, add, sv_type);
656+
}
657+
658+
GV *
659+
Perl_gv_fetchsv(pTHX_ SV *name, I32 flags, I32 sv_type) {
660+
STRLEN len;
661+
const char *nambeg = SvPV(name, len);
662+
return gv_fetchpvn_flags(nambeg, len, flags | SvUTF8(name), sv_type);
663+
}
664+
665+
GV *
666+
Perl_gv_fetchpvn_flags(pTHX_ const char *nambeg, STRLEN full_len, I32 flags,
667+
I32 sv_type)
654668
{
655669
register const char *name = nambeg;
656670
register GV *gv = 0;
657671
GV**gvp;
658672
I32 len;
659673
register const char *namend;
660674
HV *stash = 0;
675+
I32 add = flags & ~SVf_UTF8;
676+
I32 utf8 = flags & SVf_UTF8;
661677

662678
if (*name == '*' && isALPHA(name[1])) /* accidental stringify on a GV? */
663679
name++;
@@ -1819,6 +1835,22 @@ Perl_amagic_call(pTHX_ SV *left, SV *right, int method, int flags)
18191835
/*
18201836
=for apidoc is_gv_magical
18211837
1838+
Returns C<TRUE> if given the name of a magical GV. Calls is_gv_magical.
1839+
1840+
=cut
1841+
*/
1842+
1843+
bool
1844+
Perl_is_gv_magical_sv(pTHX_ SV *name, U32 flags)
1845+
{
1846+
STRLEN len;
1847+
char *temp = SvPV(name, len);
1848+
return is_gv_magical(temp, len, flags);
1849+
}
1850+
1851+
/*
1852+
=for apidoc is_gv_magical
1853+
18221854
Returns C<TRUE> if given the name of a magical GV.
18231855
18241856
Currently only useful internally when determining if a GV should be

gv.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -153,6 +153,8 @@ Return the SV from the GV.
153153
#define GV_ADDWARN 0x04 /* add, but warn if symbol wasn't already there */
154154
#define GV_ADDINEVAL 0x08 /* add, as though we're doing so within an eval */
155155
#define GV_NOINIT 0x10 /* add, but don't init symbol, if type != PVGV */
156-
156+
/* SVf_UTF8 (more accurately the return value from SvUTF8) is also valid
157+
as a flag to gv_fetch_pvn_flags, so ensure it lies outside this range.
158+
*/
157159
#define gv_fullname3(sv,gv,prefix) gv_fullname4(sv,gv,prefix,TRUE)
158160
#define gv_efullname3(sv,gv,prefix) gv_efullname4(sv,gv,prefix,TRUE)

mg.c

Lines changed: 4 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1764,16 +1764,11 @@ Perl_magic_getglob(pTHX_ SV *sv, MAGIC *mg)
17641764
int
17651765
Perl_magic_setglob(pTHX_ SV *sv, MAGIC *mg)
17661766
{
1767-
register char *s;
17681767
GV* gv;
1769-
STRLEN n_a;
1770-
1768+
17711769
if (!SvOK(sv))
17721770
return 0;
1773-
s = SvPV(sv, n_a);
1774-
if (*s == '*' && s[1])
1775-
s++;
1776-
gv = gv_fetchpv(s,TRUE, SVt_PVGV);
1771+
gv = gv_fetchsv(sv,TRUE, SVt_PVGV);
17771772
if (sv == (SV*)gv)
17781773
return 0;
17791774
if (GvGP(sv))
@@ -2212,12 +2207,12 @@ Perl_magic_set(pTHX_ SV *sv, MAGIC *mg)
22122207
case '^':
22132208
Safefree(IoTOP_NAME(GvIOp(PL_defoutgv)));
22142209
IoTOP_NAME(GvIOp(PL_defoutgv)) = s = savepv(SvPV(sv,len));
2215-
IoTOP_GV(GvIOp(PL_defoutgv)) = gv_fetchpv(s,TRUE, SVt_PVIO);
2210+
IoTOP_GV(GvIOp(PL_defoutgv)) = gv_fetchsv(sv,TRUE, SVt_PVIO);
22162211
break;
22172212
case '~':
22182213
Safefree(IoFMT_NAME(GvIOp(PL_defoutgv)));
22192214
IoFMT_NAME(GvIOp(PL_defoutgv)) = s = savepv(SvPV(sv,len));
2220-
IoFMT_GV(GvIOp(PL_defoutgv)) = gv_fetchpv(s,TRUE, SVt_PVIO);
2215+
IoFMT_GV(GvIOp(PL_defoutgv)) = gv_fetchsv(sv,TRUE, SVt_PVIO);
22212216
break;
22222217
case '=':
22232218
IoPAGE_LEN(GvIOp(PL_defoutgv)) = (SvIOK(sv) ? SvIVX(sv) : sv_2iv(sv));

op.c

Lines changed: 24 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -4204,10 +4204,13 @@ Perl_newATTRSUB(pTHX_ I32 floor, OP *o, OP *proto, OP *attrs, OP *block)
42044204
}
42054205
else
42064206
aname = Nullch;
4207-
gv = gv_fetchpv(name ? name : (aname ? aname :
4208-
(PL_curstash ? "__ANON__" : "__ANON__::__ANON__")),
4209-
GV_ADDMULTI | ((block || attrs) ? 0 : GV_NOINIT),
4210-
SVt_PVCV);
4207+
gv = name ? gv_fetchsv(cSVOPo->op_sv,
4208+
GV_ADDMULTI | ((block || attrs) ? 0 : GV_NOINIT),
4209+
SVt_PVCV)
4210+
: gv_fetchpv(aname ? aname
4211+
: (PL_curstash ? "__ANON__" : "__ANON__::__ANON__"),
4212+
GV_ADDMULTI | ((block || attrs) ? 0 : GV_NOINIT),
4213+
SVt_PVCV);
42114214

42124215
if (o)
42134216
SAVEFREEOP(o);
@@ -4675,15 +4678,13 @@ void
46754678
Perl_newFORM(pTHX_ I32 floor, OP *o, OP *block)
46764679
{
46774680
register CV *cv;
4678-
char *name;
46794681
GV *gv;
4680-
STRLEN n_a;
46814682

46824683
if (o)
4683-
name = SvPVx(cSVOPo->op_sv, n_a);
4684+
gv = gv_fetchsv(cSVOPo->op_sv, TRUE, SVt_PVFM);
46844685
else
4685-
name = "STDOUT";
4686-
gv = gv_fetchpv(name,TRUE, SVt_PVFM);
4686+
gv = gv_fetchpv("STDOUT", TRUE, SVt_PVFM);
4687+
46874688
#ifdef GV_UNIQUE_CHECK
46884689
if (GvUNIQUE(gv)) {
46894690
Perl_croak(aTHX_ "Bad symbol for form (GV is unique)");
@@ -4695,7 +4696,9 @@ Perl_newFORM(pTHX_ I32 floor, OP *o, OP *block)
46954696
line_t oldline = CopLINE(PL_curcop);
46964697
if (PL_copline != NOLINE)
46974698
CopLINE_set(PL_curcop, PL_copline);
4698-
Perl_warner(aTHX_ packWARN(WARN_REDEFINE), "Format %s redefined",name);
4699+
Perl_warner(aTHX_ packWARN(WARN_REDEFINE),
4700+
o ? "Format %"SVf" redefined"
4701+
: "Format STDOUT redefined" ,cSVOPo->op_sv);
46994702
CopLINE_set(PL_curcop, oldline);
47004703
}
47014704
SvREFCNT_dec(cv);
@@ -5109,11 +5112,9 @@ Perl_ck_rvconst(pTHX_ register OP *o)
51095112

51105113
o->op_private |= (PL_hints & HINT_STRICT_REFS);
51115114
if (kid->op_type == OP_CONST) {
5112-
char *name;
51135115
int iscv;
51145116
GV *gv;
51155117
SV *kidsv = kid->op_sv;
5116-
STRLEN n_a;
51175118

51185119
/* Is it a constant from cv_const_sv()? */
51195120
if (SvROK(kidsv) && SvREADONLY(kidsv)) {
@@ -5143,7 +5144,6 @@ Perl_ck_rvconst(pTHX_ register OP *o)
51435144
Perl_croak(aTHX_ "Constant is not %s reference", badtype);
51445145
return o;
51455146
}
5146-
name = SvPV(kidsv, n_a);
51475147
if ((PL_hints & HINT_STRICT_REFS) && (kid->op_private & OPpCONST_BARE)) {
51485148
char *badthing = Nullch;
51495149
switch (o->op_type) {
@@ -5159,8 +5159,8 @@ Perl_ck_rvconst(pTHX_ register OP *o)
51595159
}
51605160
if (badthing)
51615161
Perl_croak(aTHX_
5162-
"Can't use bareword (\"%s\") as %s ref while \"strict refs\" in use",
5163-
name, badthing);
5162+
"Can't use bareword (\"%"SVf"\") as %s ref while \"strict refs\" in use",
5163+
kidsv, badthing);
51645164
}
51655165
/*
51665166
* This is a little tricky. We only want to add the symbol if we
@@ -5172,7 +5172,7 @@ Perl_ck_rvconst(pTHX_ register OP *o)
51725172
*/
51735173
iscv = (o->op_type == OP_RV2CV) * 2;
51745174
do {
5175-
gv = gv_fetchpv(name,
5175+
gv = gv_fetchsv(kidsv,
51765176
iscv | !(kid->op_private & OPpCONST_ENTERED),
51775177
iscv
51785178
? SVt_PVCV
@@ -5215,9 +5215,8 @@ Perl_ck_ftst(pTHX_ OP *o)
52155215
SVOP *kid = (SVOP*)cUNOPo->op_first;
52165216

52175217
if (kid->op_type == OP_CONST && (kid->op_private & OPpCONST_BARE)) {
5218-
STRLEN n_a;
52195218
OP *newop = newGVOP(type, OPf_REF,
5220-
gv_fetchpv(SvPVx(kid->op_sv, n_a), TRUE, SVt_PVIO));
5219+
gv_fetchsv(kid->op_sv, TRUE, SVt_PVIO));
52215220
op_free(o);
52225221
o = newop;
52235222
return o;
@@ -5259,7 +5258,6 @@ Perl_ck_fun(pTHX_ OP *o)
52595258
}
52605259

52615260
if (o->op_flags & OPf_KIDS) {
5262-
STRLEN n_a;
52635261
tokid = &cLISTOPo->op_first;
52645262
kid = cLISTOPo->op_first;
52655263
if (kid->op_type == OP_PUSHMARK ||
@@ -5302,13 +5300,12 @@ Perl_ck_fun(pTHX_ OP *o)
53025300
if (kid->op_type == OP_CONST &&
53035301
(kid->op_private & OPpCONST_BARE))
53045302
{
5305-
char *name = SvPVx(((SVOP*)kid)->op_sv, n_a);
53065303
OP *newop = newAVREF(newGVOP(OP_GV, 0,
5307-
gv_fetchpv(name, TRUE, SVt_PVAV) ));
5304+
gv_fetchsv(((SVOP*)kid)->op_sv, TRUE, SVt_PVAV) ));
53085305
if (ckWARN2(WARN_DEPRECATED, WARN_SYNTAX))
53095306
Perl_warner(aTHX_ packWARN2(WARN_DEPRECATED, WARN_SYNTAX),
5310-
"Array @%s missing the @ in argument %"IVdf" of %s()",
5311-
name, (IV)numargs, PL_op_desc[type]);
5307+
"Array @%"SVf" missing the @ in argument %"IVdf" of %s()",
5308+
((SVOP*)kid)->op_sv, (IV)numargs, PL_op_desc[type]);
53125309
op_free(kid);
53135310
kid = newop;
53145311
kid->op_sibling = sibl;
@@ -5322,13 +5319,12 @@ Perl_ck_fun(pTHX_ OP *o)
53225319
if (kid->op_type == OP_CONST &&
53235320
(kid->op_private & OPpCONST_BARE))
53245321
{
5325-
char *name = SvPVx(((SVOP*)kid)->op_sv, n_a);
53265322
OP *newop = newHVREF(newGVOP(OP_GV, 0,
5327-
gv_fetchpv(name, TRUE, SVt_PVHV) ));
5323+
gv_fetchsv(((SVOP*)kid)->op_sv, TRUE, SVt_PVHV) ));
53285324
if (ckWARN2(WARN_DEPRECATED, WARN_SYNTAX))
53295325
Perl_warner(aTHX_ packWARN2(WARN_DEPRECATED, WARN_SYNTAX),
5330-
"Hash %%%s missing the %% in argument %"IVdf" of %s()",
5331-
name, (IV)numargs, PL_op_desc[type]);
5326+
"Hash %%%"SVf" missing the %% in argument %"IVdf" of %s()",
5327+
((SVOP*)kid)->op_sv, (IV)numargs, PL_op_desc[type]);
53325328
op_free(kid);
53335329
kid = newop;
53345330
kid->op_sibling = sibl;
@@ -5355,8 +5351,7 @@ Perl_ck_fun(pTHX_ OP *o)
53555351
(kid->op_private & OPpCONST_BARE))
53565352
{
53575353
OP *newop = newGVOP(OP_GV, 0,
5358-
gv_fetchpv(SvPVx(((SVOP*)kid)->op_sv, n_a), TRUE,
5359-
SVt_PVIO) );
5354+
gv_fetchsv(((SVOP*)kid)->op_sv, TRUE, SVt_PVIO) );
53605355
if (!(o->op_private & 1) && /* if not unop */
53615356
kid == cLISTOPo->op_last)
53625357
cLISTOPo->op_last = newop;

perl.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3239,6 +3239,8 @@ EXTCONST char PL_no_wrongref[]
32393239
INIT("Can't use %s ref as %s ref");
32403240
EXTCONST char PL_no_symref[]
32413241
INIT("Can't use string (\"%.32s\") as %s ref while \"strict refs\" in use");
3242+
EXTCONST char PL_no_symref_sv[]
3243+
INIT("Can't use string (\"%.32" SVf "\") as %s ref while \"strict refs\" in use");
32423244
EXTCONST char PL_no_usym[]
32433245
INIT("Can't use an undefined value as %s reference");
32443246
EXTCONST char PL_no_aelem[]

pp.c

Lines changed: 12 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -147,9 +147,6 @@ PP(pp_rv2gv)
147147
}
148148
else {
149149
if (SvTYPE(sv) != SVt_PVGV) {
150-
char *sym;
151-
STRLEN len;
152-
153150
if (SvGMAGICAL(sv)) {
154151
mg_get(sv);
155152
if (SvROK(sv))
@@ -195,22 +192,21 @@ PP(pp_rv2gv)
195192
report_uninit(sv);
196193
RETSETUNDEF;
197194
}
198-
sym = SvPV(sv,len);
199195
if ((PL_op->op_flags & OPf_SPECIAL) &&
200196
!(PL_op->op_flags & OPf_MOD))
201197
{
202-
sv = (SV*)gv_fetchpv(sym, FALSE, SVt_PVGV);
203-
if (!sv
204-
&& (!is_gv_magical(sym,len,0)
205-
|| !(sv = (SV*)gv_fetchpv(sym, TRUE, SVt_PVGV))))
206-
{
198+
SV * temp = (SV*)gv_fetchsv(sv, FALSE, SVt_PVGV);
199+
if (!temp
200+
&& (!is_gv_magical_sv(sv,0)
201+
|| !(sv = (SV*)gv_fetchsv(sv, TRUE, SVt_PVGV)))) {
207202
RETSETUNDEF;
208203
}
204+
sv = temp;
209205
}
210206
else {
211207
if (PL_op->op_private & HINT_STRICT_REFS)
212-
DIE(aTHX_ PL_no_symref, sym, "a symbol");
213-
sv = (SV*)gv_fetchpv(sym, TRUE, SVt_PVGV);
208+
DIE(aTHX_ PL_no_symref_sv, sv, "a symbol");
209+
sv = (SV*)gv_fetchsv(sv, TRUE, SVt_PVGV);
214210
}
215211
}
216212
}
@@ -238,8 +234,6 @@ PP(pp_rv2sv)
238234
}
239235
}
240236
else {
241-
char *sym;
242-
STRLEN len;
243237
gv = (GV*)sv;
244238

245239
if (SvTYPE(gv) != SVt_PVGV) {
@@ -256,22 +250,21 @@ PP(pp_rv2sv)
256250
report_uninit(sv);
257251
RETSETUNDEF;
258252
}
259-
sym = SvPV(sv, len);
260253
if ((PL_op->op_flags & OPf_SPECIAL) &&
261254
!(PL_op->op_flags & OPf_MOD))
262255
{
263-
gv = (GV*)gv_fetchpv(sym, FALSE, SVt_PV);
256+
gv = (GV*)gv_fetchsv(sv, FALSE, SVt_PV);
264257
if (!gv
265-
&& (!is_gv_magical(sym,len,0)
266-
|| !(gv = (GV*)gv_fetchpv(sym, TRUE, SVt_PV))))
258+
&& (!is_gv_magical_sv(sv, 0)
259+
|| !(gv = (GV*)gv_fetchsv(sv, TRUE, SVt_PV))))
267260
{
268261
RETSETUNDEF;
269262
}
270263
}
271264
else {
272265
if (PL_op->op_private & HINT_STRICT_REFS)
273-
DIE(aTHX_ PL_no_symref, sym, "a SCALAR");
274-
gv = (GV*)gv_fetchpv(sym, TRUE, SVt_PV);
266+
DIE(aTHX_ PL_no_symref_sv, sv, "a SCALAR");
267+
gv = (GV*)gv_fetchsv(sv, TRUE, SVt_PV);
275268
}
276269
}
277270
sv = GvSV(gv);

0 commit comments

Comments
 (0)