3 * Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004,
4 * 2005, 2006, 2007, 2008 by Larry Wall and others
6 * You may distribute under the terms of either the GNU General Public
7 * License or the Artistic License, as specified in the README file.
12 * '"The roots of those mountains must be roots indeed; there must be
13 * great secrets buried there which have not been discovered since the
14 * beginning."' --Gandalf, relating Gollum's history
16 * [p.54 of _The Lord of the Rings_, I/ii: "The Shadow of the Past"]
19 /* This file contains the code that implements the functions in Perl's
20 * UNIVERSAL package, such as UNIVERSAL->can().
22 * It is also used to store XS functions that need to be present in
23 * miniperl for a lack of a better place to put them. It might be
24 * clever to move them to separate XS files which would then be pulled
25 * in by some to-be-written build process.
29 #define PERL_IN_UNIVERSAL_C
32 #if defined(USE_PERLIO)
33 #include "perliol.h" /* For the PERLIO_F_XXX */
37 * Contributed by Graham Barr <Graham.Barr@tiuk.ti.com>
38 * The main guts of traverse_isa was actually copied from gv_fetchmeth
41 #define PERL_ARGS_ASSERT_ISA_LOOKUP \
43 assert(namesv || name)
47 S_isa_lookup(pTHX_ HV *stash, SV *namesv, const char * name, STRLEN len, U32 flags)
49 const struct mro_meta *const meta = HvMROMETA(stash);
53 PERL_ARGS_ASSERT_ISA_LOOKUP;
56 (void)mro_get_linear_isa(stash);
60 if (hv_common(isa, namesv, name, len, ( flags & SVf_UTF8 ? HVhek_UTF8 : 0),
61 HV_FETCH_ISEXISTS, NULL, 0)) {
62 /* Direct name lookup worked. */
66 /* A stash/class can go by many names (ie. User == main::User), so
67 we use the HvENAME in the stash itself, which is canonical, falling
68 back to HvNAME if necessary. */
69 our_stash = gv_stashsvpvn_cached(namesv, name, len, flags);
72 HEK *canon_name = HvENAME_HEK(our_stash);
73 if (!canon_name) canon_name = HvNAME_HEK(our_stash);
75 if (hv_common(isa, NULL, HEK_KEY(canon_name), HEK_LEN(canon_name),
76 HEK_FLAGS(canon_name),
77 HV_FETCH_ISEXISTS, NULL, HEK_HASH(canon_name))) {
85 #define PERL_ARGS_ASSERT_SV_DERIVED_FROM_SVPVN \
87 assert(namesv || name)
90 S_sv_derived_from_svpvn(pTHX_ SV *sv, SV *namesv, const char * name, const STRLEN len, U32 flags)
94 PERL_ARGS_ASSERT_SV_DERIVED_FROM_SVPVN;
100 type = sv_reftype(sv,0);
103 name = SvPV_nolen(namesv);
104 if (strEQ(name, type))
112 stash = gv_stashsv(sv, 0);
115 if (stash && isa_lookup(stash, namesv, name, len, flags))
118 stash = gv_stashpvs("UNIVERSAL", 0);
119 return stash && isa_lookup(stash, namesv, name, len, flags);
123 =head1 SV Manipulation Functions
125 =for apidoc sv_derived_from_pvn
127 Returns a boolean indicating whether the SV is derived from the specified class
128 I<at the C level>. To check derivation at the Perl level, call C<isa()> as a
131 Currently, the only significant value for C<flags> is SVf_UTF8.
135 =for apidoc sv_derived_from_sv
137 Exactly like L</sv_derived_from_pvn>, but takes the name string in the form
138 of an SV instead of a string/length pair. This is the advised form.
145 Perl_sv_derived_from_sv(pTHX_ SV *sv, SV *namesv, U32 flags)
147 PERL_ARGS_ASSERT_SV_DERIVED_FROM_SV;
148 return sv_derived_from_svpvn(sv, namesv, NULL, 0, flags);
152 =for apidoc sv_derived_from
154 Exactly like L</sv_derived_from_pv>, but doesn't take a C<flags> parameter.
160 Perl_sv_derived_from(pTHX_ SV *sv, const char *const name)
162 PERL_ARGS_ASSERT_SV_DERIVED_FROM;
163 return sv_derived_from_svpvn(sv, NULL, name, strlen(name), 0);
167 =for apidoc sv_derived_from_pv
169 Exactly like L</sv_derived_from_pvn>, but takes a nul-terminated string
170 instead of a string/length pair.
177 Perl_sv_derived_from_pv(pTHX_ SV *sv, const char *const name, U32 flags)
179 PERL_ARGS_ASSERT_SV_DERIVED_FROM_PV;
180 return sv_derived_from_svpvn(sv, NULL, name, strlen(name), flags);
184 Perl_sv_derived_from_pvn(pTHX_ SV *sv, const char *const name, const STRLEN len, U32 flags)
186 PERL_ARGS_ASSERT_SV_DERIVED_FROM_PVN;
187 return sv_derived_from_svpvn(sv, NULL, name, len, flags);
191 =for apidoc sv_does_sv
193 Returns a boolean indicating whether the SV performs a specific, named role.
194 The SV can be a Perl object or the name of a Perl class.
202 Perl_sv_does_sv(pTHX_ SV *sv, SV *namesv, U32 flags)
209 PERL_ARGS_ASSERT_SV_DOES_SV;
210 PERL_UNUSED_ARG(flags);
217 if (!SvOK(sv) || !(SvROK(sv) || (SvPOK(sv) && SvCUR(sv)))) {
222 if (SvROK(sv) && SvOBJECT(SvRV(sv))) {
223 classname = sv_ref(NULL,SvRV(sv),TRUE);
228 if (sv_eq(classname, namesv)) {
239 /* create a PV with value "isa", but with a special address
240 * so that perl knows we're really doing "DOES" instead */
241 methodname = newSV_type(SVt_PV);
242 SvLEN_set(methodname, 0);
243 SvCUR_set(methodname, strlen(PL_isa_DOES));
244 SvPVX(methodname) = (char *)PL_isa_DOES; /* discard 'const' qualifier */
245 SvPOK_on(methodname);
246 sv_2mortal(methodname);
247 call_sv(methodname, G_SCALAR | G_METHOD);
250 does_it = SvTRUE_NN( TOPs );
260 Like L</sv_does_pv>, but doesn't take a C<flags> parameter.
266 Perl_sv_does(pTHX_ SV *sv, const char *const name)
268 PERL_ARGS_ASSERT_SV_DOES;
269 return sv_does_sv(sv, newSVpvn_flags(name, strlen(name), SVs_TEMP), 0);
273 =for apidoc sv_does_pv
275 Like L</sv_does_sv>, but takes a nul-terminated string instead of an SV.
282 Perl_sv_does_pv(pTHX_ SV *sv, const char *const name, U32 flags)
284 PERL_ARGS_ASSERT_SV_DOES_PV;
285 return sv_does_sv(sv, newSVpvn_flags(name, strlen(name), SVs_TEMP | flags), flags);
289 =for apidoc sv_does_pvn
291 Like L</sv_does_sv>, but takes a string/length pair instead of an SV.
297 Perl_sv_does_pvn(pTHX_ SV *sv, const char *const name, const STRLEN len, U32 flags)
299 PERL_ARGS_ASSERT_SV_DOES_PVN;
301 return sv_does_sv(sv, newSVpvn_flags(name, len, flags | SVs_TEMP), flags);
305 =for apidoc croak_xs_usage
307 A specialised variant of C<croak()> for emitting the usage message for xsubs
309 croak_xs_usage(cv, "eee_yow");
311 works out the package name and subroutine name from C<cv>, and then calls
312 C<croak()>. Hence if C<cv> is C<&ouch::awk>, it would call C<croak> as:
314 Perl_croak(aTHX_ "Usage: %" SVf "::%" SVf "(%s)", "ouch" "awk",
321 Perl_croak_xs_usage(const CV *const cv, const char *const params)
323 /* Avoid CvGV as it requires aTHX. */
324 const GV *gv = CvNAMED(cv) ? NULL : cv->sv_any->xcv_gv_u.xcv_gv;
326 PERL_ARGS_ASSERT_CROAK_XS_USAGE;
329 const HV *const stash = GvSTASH(gv);
331 if (HvNAME_get(stash))
332 /* diag_listed_as: SKIPME */
333 Perl_croak_nocontext("Usage: %" HEKf "::%" HEKf "(%s)",
334 HEKfARG(HvNAME_HEK(stash)),
335 HEKfARG(GvNAME_HEK(gv)),
338 /* diag_listed_as: SKIPME */
339 Perl_croak_nocontext("Usage: %" HEKf "(%s)",
340 HEKfARG(GvNAME_HEK(gv)), params);
343 if ((gv = CvGV(cv))) goto got_gv;
345 /* Pants. I don't think that it should be possible to get here. */
346 /* diag_listed_as: SKIPME */
347 Perl_croak(aTHX_ "Usage: CODE(0x%" UVxf ")(%s)", PTR2UV(cv), params);
351 XS(XS_UNIVERSAL_isa); /* prototype to pass -Wmissing-prototypes */
357 croak_xs_usage(cv, "reference, kind");
359 SV * const sv = ST(0);
363 if (!SvOK(sv) || !(SvROK(sv) || (SvPOK(sv) && SvCUR(sv))))
366 ST(0) = boolSV(sv_derived_from_sv(sv, ST(1), 0));
371 XS(XS_UNIVERSAL_can); /* prototype to pass -Wmissing-prototypes */
381 croak_xs_usage(cv, "object-ref, method");
387 /* Reject undef and empty string. Note that the string form takes
388 precedence here over the numeric form, as (!1)->foo treats the
389 invocant as the empty string, though it is a dualvar. */
390 if (!SvOK(sv) || (SvPOK(sv) && !SvCUR(sv)))
396 sv = MUTABLE_SV(SvRV(sv));
399 else if (isGV_with_GP(sv) && GvIO(sv))
400 pkg = SvSTASH(GvIO(sv));
402 else if (isGV_with_GP(sv) && GvIO(sv))
403 pkg = SvSTASH(GvIO(sv));
404 else if ((iogv = gv_fetchsv_nomg(sv, 0, SVt_PVIO)) && GvIO(iogv))
405 pkg = SvSTASH(GvIO(iogv));
407 pkg = gv_stashsv(sv, 0);
409 pkg = gv_stashpvs("UNIVERSAL", 0);
413 GV * const gv = gv_fetchmethod_sv_flags(pkg, ST(1), 0);
415 rv = sv_2mortal(newRV(MUTABLE_SV(GvCV(gv))));
422 XS(XS_UNIVERSAL_DOES); /* prototype to pass -Wmissing-prototypes */
423 XS(XS_UNIVERSAL_DOES)
429 Perl_croak(aTHX_ "Usage: invocant->DOES(kind)");
431 SV * const sv = ST(0);
432 if (sv_does_sv( sv, ST(1), 0 ))
439 XS(XS_utf8_is_utf8); /* prototype to pass -Wmissing-prototypes */
444 croak_xs_usage(cv, "sv");
446 SV * const sv = ST(0);
456 XS(XS_utf8_valid); /* prototype to pass -Wmissing-prototypes */
461 croak_xs_usage(cv, "sv");
463 SV * const sv = ST(0);
465 const char * const s = SvPV_const(sv,len);
466 if (!SvUTF8(sv) || is_utf8_string((const U8*)s,len))
474 XS(XS_utf8_encode); /* prototype to pass -Wmissing-prototypes */
479 croak_xs_usage(cv, "sv");
480 sv_utf8_encode(ST(0));
485 XS(XS_utf8_decode); /* prototype to pass -Wmissing-prototypes */
490 croak_xs_usage(cv, "sv");
492 SV * const sv = ST(0);
494 SvPV_force_nolen(sv);
495 RETVAL = sv_utf8_decode(sv);
497 ST(0) = boolSV(RETVAL);
502 XS(XS_utf8_upgrade); /* prototype to pass -Wmissing-prototypes */
507 croak_xs_usage(cv, "sv");
509 SV * const sv = ST(0);
513 RETVAL = sv_utf8_upgrade(sv);
514 XSprePUSH; PUSHi((IV)RETVAL);
519 XS(XS_utf8_downgrade); /* prototype to pass -Wmissing-prototypes */
520 XS(XS_utf8_downgrade)
523 if (items < 1 || items > 2)
524 croak_xs_usage(cv, "sv, failok=0");
526 SV * const sv0 = ST(0);
527 SV * const sv1 = ST(1);
528 const bool failok = (items < 2) ? 0 : SvTRUE_NN(sv1) ? 1 : 0;
529 const bool RETVAL = sv_utf8_downgrade(sv0, failok);
531 ST(0) = boolSV(RETVAL);
536 XS(XS_utf8_native_to_unicode); /* prototype to pass -Wmissing-prototypes */
537 XS(XS_utf8_native_to_unicode)
540 const UV uv = SvUV(ST(0));
543 croak_xs_usage(cv, "sv");
545 ST(0) = sv_2mortal(newSVuv(NATIVE_TO_UNI(uv)));
549 XS(XS_utf8_unicode_to_native); /* prototype to pass -Wmissing-prototypes */
550 XS(XS_utf8_unicode_to_native)
553 const UV uv = SvUV(ST(0));
556 croak_xs_usage(cv, "sv");
558 ST(0) = sv_2mortal(newSVuv(UNI_TO_NATIVE(uv)));
562 XS(XS_Internals_SvREADONLY); /* prototype to pass -Wmissing-prototypes */
563 XS(XS_Internals_SvREADONLY) /* This is dangerous stuff. */
566 SV * const svz = ST(0);
569 /* [perl #77776] - called as &foo() not foo() */
571 croak_xs_usage(cv, "SCALAR[, ON]");
581 else if (items == 2) {
583 if (SvTRUE_NN(sv1)) {
584 SvFLAGS(sv) |= SVf_READONLY;
588 /* I hope you really know what you are doing. */
589 SvFLAGS(sv) &=~ SVf_READONLY;
593 XSRETURN_UNDEF; /* Can't happen. */
596 XS(XS_constant__make_const); /* prototype to pass -Wmissing-prototypes */
597 XS(XS_constant__make_const) /* This is dangerous stuff. */
600 SV * const svz = ST(0);
603 /* [perl #77776] - called as &foo() not foo() */
604 if (!SvROK(svz) || items != 1)
605 croak_xs_usage(cv, "SCALAR");
610 if (SvTYPE(sv) == SVt_PVAV && AvFILLp(sv) != -1) {
611 /* for constant.pm; nobody else should be calling this
614 for (svp = AvARRAY(sv) + AvFILLp(sv)
617 if (*svp) SvPADTMP_on(*svp);
622 XS(XS_Internals_SvREFCNT); /* prototype to pass -Wmissing-prototypes */
623 XS(XS_Internals_SvREFCNT) /* This is dangerous stuff. */
626 SV * const svz = ST(0);
630 /* [perl #77776] - called as &foo() not foo() */
631 if ((items != 1 && items != 2) || !SvROK(svz))
632 croak_xs_usage(cv, "SCALAR[, REFCOUNT]");
636 /* I hope you really know what you are doing. */
637 /* idea is for SvREFCNT(sv) to be accessed only once */
638 refcnt = items == 2 ?
639 /* we free one ref on exit */
640 (SvREFCNT(sv) = SvUV(ST(1)) + 1)
642 XSRETURN_UV(refcnt - 1); /* Minus the ref created for us. */
646 XS(XS_Internals_hv_clear_placehold); /* prototype to pass -Wmissing-prototypes */
647 XS(XS_Internals_hv_clear_placehold)
651 if (items != 1 || !SvROK(ST(0)))
652 croak_xs_usage(cv, "hv");
654 HV * const hv = MUTABLE_HV(SvRV(ST(0)));
655 hv_clear_placeholders(hv);
660 XS(XS_PerlIO_get_layers); /* prototype to pass -Wmissing-prototypes */
661 XS(XS_PerlIO_get_layers)
664 if (items < 1 || items % 2 == 0)
665 croak_xs_usage(cv, "filehandle[,args]");
666 #if defined(USE_PERLIO)
672 bool details = FALSE;
676 for (svp = MARK + 2; svp <= SP; svp += 2) {
677 SV * const * const varp = svp;
678 SV * const * const valp = svp + 1;
680 const char * const key = SvPV_const(*varp, klen);
684 if (memEQs(key, klen, "input")) {
685 input = SvTRUE(*valp);
690 if (memEQs(key, klen, "output")) {
691 input = !SvTRUE(*valp);
696 if (memEQs(key, klen, "details")) {
697 details = SvTRUE(*valp);
704 "get_layers: unknown argument '%s'",
713 gv = MAYBE_DEREF_GV(sv);
715 if (!gv && !SvROK(sv))
716 gv = gv_fetchsv_nomg(sv, 0, SVt_PVIO);
718 if (gv && (io = GvIO(gv))) {
719 AV* const av = PerlIO_get_layers(aTHX_ input ?
720 IoIFP(io) : IoOFP(io));
722 const SSize_t last = av_tindex(av);
725 for (i = last; i >= 0; i -= 3) {
726 SV * const * const namsvp = av_fetch(av, i - 2, FALSE);
727 SV * const * const argsvp = av_fetch(av, i - 1, FALSE);
728 SV * const * const flgsvp = av_fetch(av, i, FALSE);
730 const bool namok = namsvp && *namsvp && SvPOK(*namsvp);
731 const bool argok = argsvp && *argsvp && SvPOK(*argsvp);
732 const bool flgok = flgsvp && *flgsvp && SvIOK(*flgsvp);
734 EXTEND(SP, 3); /* Three is the max in all branches: better check just once */
736 /* Indents of 5? Yuck. */
737 /* We know that PerlIO_get_layers creates a new SV for
738 the name and flags, so we can just take a reference
739 and "steal" it when we free the AV below. */
741 ? sv_2mortal(SvREFCNT_inc_simple_NN(*namsvp))
744 ? newSVpvn_flags(SvPVX_const(*argsvp),
746 (SvUTF8(*argsvp) ? SVf_UTF8 : 0)
750 ? sv_2mortal(SvREFCNT_inc_simple_NN(*flgsvp))
756 PUSHs(sv_2mortal(Perl_newSVpvf(aTHX_ "%" SVf "(%" SVf ")",
760 PUSHs(sv_2mortal(SvREFCNT_inc_simple_NN(*namsvp)));
765 const IV flags = SvIVX(*flgsvp);
767 if (flags & PERLIO_F_UTF8) {
768 PUSHs(newSVpvs_flags("utf8", SVs_TEMP));
785 XS(XS_re_is_regexp); /* prototype to pass -Wmissing-prototypes */
791 croak_xs_usage(cv, "sv");
800 XS(XS_re_regnames_count); /* prototype to pass -Wmissing-prototypes */
801 XS(XS_re_regnames_count)
803 REGEXP *rx = PL_curpm ? PM_GETRE(PL_curpm) : NULL;
808 croak_xs_usage(cv, "");
813 ret = CALLREG_NAMED_BUFF_COUNT(rx);
816 PUSHs(ret ? sv_2mortal(ret) : &PL_sv_undef);
820 XS(XS_re_regname); /* prototype to pass -Wmissing-prototypes */
828 if (items < 1 || items > 2)
829 croak_xs_usage(cv, "name[, all ]");
834 rx = PL_curpm ? PM_GETRE(PL_curpm) : NULL;
839 if (items == 2 && SvTRUE_NN(ST(1))) {
844 ret = CALLREG_NAMED_BUFF_FETCH(rx, ST(0), (flags | RXapif_REGNAME));
847 PUSHs(ret ? sv_2mortal(ret) : &PL_sv_undef);
852 XS(XS_re_regnames); /* prototype to pass -Wmissing-prototypes */
865 croak_xs_usage(cv, "[all]");
867 rx = PL_curpm ? PM_GETRE(PL_curpm) : NULL;
872 if (items == 1 && SvTRUE_NN(ST(0))) {
881 ret = CALLREG_NAMED_BUFF_ALL(rx, (flags | RXapif_REGNAMES));
888 av = MUTABLE_AV(SvRV(ret));
889 length = av_tindex(av);
891 EXTEND(SP, length+1); /* better extend stack just once */
892 for (i = 0; i <= length; i++) {
893 entry = av_fetch(av, i, FALSE);
896 Perl_croak(aTHX_ "NULL array element in re::regnames()");
898 mPUSHs(SvREFCNT_inc_simple_NN(*entry));
907 XS(XS_re_regexp_pattern); /* prototype to pass -Wmissing-prototypes */
908 XS(XS_re_regexp_pattern)
912 U8 const gimme = GIMME_V;
917 croak_xs_usage(cv, "sv");
920 Checks if a reference is a regex or not. If the parameter is
921 not a ref, or is not the result of a qr// then returns false
922 in scalar context and an empty list in list context.
923 Otherwise in list context it returns the pattern and the
924 modifiers, in scalar context it returns the pattern just as it
925 would if the qr// was stringified normally, regardless as
926 to the class of the variable and any stringification overloads
930 if ((re = SvRX(ST(0)))) /* assign deliberate */
932 /* Houston, we have a regex! */
935 if ( gimme == G_ARRAY ) {
937 char reflags[sizeof(INT_PAT_MODS) + MAX_CHARSET_NAME_LENGTH];
943 we are in list context so stringify
944 the modifiers that apply. We ignore "negative
945 modifiers" in this scenario, and the default character set
948 if (get_regex_charset(RX_EXTFLAGS(re)) != REGEX_DEPENDS_CHARSET) {
950 const char* const name = get_regex_charset_name(RX_EXTFLAGS(re),
952 Copy(name, reflags + left, len, char);
956 match_flags = (U16)((RX_EXTFLAGS(re) & RXf_PMf_COMPILETIME)
957 >> RXf_PMf_STD_PMMOD_SHIFT);
959 while((ch = *fptr++)) {
960 if(match_flags & 1) {
961 reflags[left++] = ch;
966 pattern = newSVpvn_flags(RX_PRECOMP(re),RX_PRELEN(re),
967 (RX_UTF8(re) ? SVf_UTF8 : 0) | SVs_TEMP);
969 /* return the pattern and the modifiers */
971 PUSHs(newSVpvn_flags(reflags, left, SVs_TEMP));
974 /* Scalar, so use the string that Perl would return */
975 /* return the pattern in (?msixn:..) format */
976 pattern = sv_2mortal(newSVsv(MUTABLE_SV(re)));
981 /* It ain't a regexp folks */
982 if ( gimme == G_ARRAY ) {
983 /* return the empty list */
986 /* Because of the (?:..) wrapping involved in a
987 stringified pattern it is impossible to get a
988 result for a real regexp that would evaluate to
989 false. Therefore we can return PL_sv_no to signify
990 that the object is not a regex, this means that one
993 if (regex($might_be_a_regex) eq '(?:foo)') { }
995 and not worry about undefined values.
1000 NOT_REACHED; /* NOTREACHED */
1005 XS(XS_Internals_getcwd)
1008 SV *sv = sv_newmortal();
1011 croak_xs_usage(cv, "");
1013 (void)getcwd_sv(sv);
1025 struct xsub_details {
1031 static const struct xsub_details these_details[] = {
1032 {"UNIVERSAL::isa", XS_UNIVERSAL_isa, NULL},
1033 {"UNIVERSAL::can", XS_UNIVERSAL_can, NULL},
1034 {"UNIVERSAL::DOES", XS_UNIVERSAL_DOES, NULL},
1035 #define VXS_XSUB_DETAILS
1037 #undef VXS_XSUB_DETAILS
1038 {"utf8::is_utf8", XS_utf8_is_utf8, NULL},
1039 {"utf8::valid", XS_utf8_valid, NULL},
1040 {"utf8::encode", XS_utf8_encode, NULL},
1041 {"utf8::decode", XS_utf8_decode, NULL},
1042 {"utf8::upgrade", XS_utf8_upgrade, NULL},
1043 {"utf8::downgrade", XS_utf8_downgrade, NULL},
1044 {"utf8::native_to_unicode", XS_utf8_native_to_unicode, NULL},
1045 {"utf8::unicode_to_native", XS_utf8_unicode_to_native, NULL},
1046 {"Internals::SvREADONLY", XS_Internals_SvREADONLY, "\\[$%@];$"},
1047 {"Internals::SvREFCNT", XS_Internals_SvREFCNT, "\\[$%@];$"},
1048 {"Internals::hv_clear_placeholders", XS_Internals_hv_clear_placehold, "\\%"},
1049 {"constant::_make_const", XS_constant__make_const, "\\[$@]"},
1050 {"PerlIO::get_layers", XS_PerlIO_get_layers, "*;@"},
1051 {"re::is_regexp", XS_re_is_regexp, "$"},
1052 {"re::regname", XS_re_regname, ";$$"},
1053 {"re::regnames", XS_re_regnames, ";$"},
1054 {"re::regnames_count", XS_re_regnames_count, ""},
1055 {"re::regexp_pattern", XS_re_regexp_pattern, "$"},
1057 {"Internals::getcwd", XS_Internals_getcwd, ""},
1062 optimize_out_native_convert_function(pTHX_ OP* entersubop,
1066 /* Optimizes out an identity function, i.e., one that just returns its
1067 * argument. The passed in function is assumed to be an identity function,
1068 * with no checking. This is designed to be called for utf8_to_native()
1069 * and native_to_utf8() on ASCII platforms, as they just return their
1070 * arguments, but it could work on any such function.
1072 * The code is mostly just cargo-culted from Memoize::Lift */
1076 SV* prototype = newSVpvs("$");
1078 PERL_UNUSED_ARG(protosv);
1080 assert(entersubop->op_type == OP_ENTERSUB);
1082 entersubop = ck_entersub_args_proto(entersubop, namegv, prototype);
1083 parent = entersubop;
1085 SvREFCNT_dec(prototype);
1087 pushop = cUNOPx(entersubop)->op_first;
1088 if (! OpHAS_SIBLING(pushop)) {
1090 pushop = cUNOPx(pushop)->op_first;
1092 argop = OpSIBLING(pushop);
1094 /* Carry on without doing the optimization if it is not something we're
1095 * expecting, so continues to work */
1097 || ! OpHAS_SIBLING(argop)
1098 || OpHAS_SIBLING(OpSIBLING(argop))
1103 /* cut argop from the subtree */
1104 (void)op_sibling_splice(parent, pushop, 1, NULL);
1106 op_free(entersubop);
1111 Perl_boot_core_UNIVERSAL(pTHX)
1113 static const char file[] = __FILE__;
1114 const struct xsub_details *xsub = these_details;
1115 const struct xsub_details *end = C_ARRAY_END(these_details);
1118 newXS_flags(xsub->name, xsub->xsub, file, xsub->proto, 0);
1119 } while (++xsub < end);
1122 { /* On ASCII platforms these functions just return their argument, so can
1123 be optimized away */
1125 CV* to_native_cv = get_cv("utf8::unicode_to_native", 0);
1126 CV* to_unicode_cv = get_cv("utf8::native_to_unicode", 0);
1128 cv_set_call_checker_flags(to_native_cv,
1129 optimize_out_native_convert_function,
1130 (SV*) to_native_cv, 0);
1131 cv_set_call_checker_flags(to_unicode_cv,
1132 optimize_out_native_convert_function,
1133 (SV*) to_unicode_cv, 0);
1137 /* Providing a Regexp::DESTROY fixes #21347. See test in t/op/ref.t */
1140 newCONSTSUB(get_hv("Regexp::", GV_ADD), "DESTROY", NULL);
1141 char ** cvfile = &CvFILE(cv);
1142 char * oldfile = *cvfile;
1144 *cvfile = (char *)file;
1150 * ex: set ts=8 sts=4 sw=4 et: