/*
+=head1 SV Manipulation Functions
+
=for apidoc sv_add_arena
Given a chunk of memory, link it to the head of the list of arenas,
return visited;
}
+#ifdef DEBUGGING
+
/* called by sv_report_used() for each live SV */
static void
sv_dump(sv);
}
}
+#endif
/*
=for apidoc sv_report_used
void
Perl_sv_report_used(pTHX)
{
+#ifdef DEBUGGING
visit(do_report_used);
+#endif
}
/* called by sv_clean_objs() for each live SV */
SvPVX(sv) = 0;
HvFILL(sv) = 0;
HvMAX(sv) = 0;
- HvKEYS(sv) = 0;
- SvNVX(sv) = 0.0;
+ HvTOTALKEYS(sv) = 0;
+ HvPLACEHOLDERS(sv) = 0;
SvMAGIC(sv) = magic;
SvSTASH(sv) = stash;
HvRITER(sv) = 0;
char *limit = tmpbuf + sizeof(tmpbuf) - 8;
/* each *s can expand to 4 chars + "...\0",
i.e. need room for 8 chars */
-
+
char *s, *end;
for (s = SvPVX(sv), end = s + SvCUR(sv); s < end && d < limit; s++) {
int ch = *s & 0xFF;
STATIC int
S_sv_2iuv_non_preserve(pTHX_ register SV *sv, I32 numtype)
{
- DEBUG_c(PerlIO_printf(Perl_debug_log,"sv_2iuv_non '%s', IV=0x%"UVxf" NV=%g inttype=%"UVXf"\n", SvPVX(sv), SvIVX(sv), SvNVX(sv), (UV)numtype));
+ DEBUG_c(PerlIO_printf(Perl_debug_log,"sv_2iuv_non '%s', IV=0x%"UVxf" NV=%"NVgf" inttype=%"UVXf"\n", SvPVX(sv), SvIVX(sv), SvNVX(sv), (UV)numtype));
if (SvNVX(sv) < (NV)IV_MIN) {
(void)SvIOKp_on(sv);
(void)SvNOK_on(sv);
SvIVX(sv) = -(IV)value;
} else {
/* Too negative for an IV. This is a double upgrade, but
- I'm assuming it will be be rare. */
+ I'm assuming it will be rare. */
if (SvTYPE(sv) < SVt_PVNV)
sv_upgrade(sv, SVt_PVNV);
SvNOK_on(sv);
DEBUG_c(PerlIO_printf(Perl_debug_log, "0x%"UVxf" 2iv(%" PERL_PRIgldbl ")\n",
PTR2UV(sv), SvNVX(sv)));
#else
- DEBUG_c(PerlIO_printf(Perl_debug_log, "0x%"UVxf" 2iv(%g)\n",
+ DEBUG_c(PerlIO_printf(Perl_debug_log, "0x%"UVxf" 2iv(%"NVgf")\n",
PTR2UV(sv), SvNVX(sv)));
#endif
this NV is in the preserved range, therefore: */
if (!(U_V(SvNVX(sv) > 0 ? SvNVX(sv) : -SvNVX(sv))
< (UV)IV_MAX)) {
- Perl_croak(aTHX_ "sv_2iv assumed (U_V(fabs(SvNVX(sv))) < (UV)IV_MAX) but SvNVX(sv)=%g U_V is 0x%"UVxf", IV_MAX is 0x%"UVxf"\n", SvNVX(sv), U_V(SvNVX(sv)), (UV)IV_MAX);
+ Perl_croak(aTHX_ "sv_2iv assumed (U_V(fabs(SvNVX(sv))) < (UV)IV_MAX) but SvNVX(sv)=%"NVgf" U_V is 0x%"UVxf", IV_MAX is 0x%"UVxf"\n", SvNVX(sv), U_V(SvNVX(sv)), (UV)IV_MAX);
}
} else {
/* IN_UV NOT_INT
SvIVX(sv) = -(IV)value;
} else {
/* Too negative for an IV. This is a double upgrade, but
- I'm assuming it will be be rare. */
+ I'm assuming it will be rare. */
if (SvTYPE(sv) < SVt_PVNV)
sv_upgrade(sv, SVt_PVNV);
SvNOK_on(sv);
DEBUG_c(PerlIO_printf(Perl_debug_log, "0x%"UVxf" 2uv(%" PERL_PRIgldbl ")\n",
PTR2UV(sv), SvNVX(sv)));
#else
- DEBUG_c(PerlIO_printf(Perl_debug_log, "0x%"UVxf" 2uv(%g)\n",
+ DEBUG_c(PerlIO_printf(Perl_debug_log, "0x%"UVxf" 2uv(%"NVgf")\n",
PTR2UV(sv), SvNVX(sv)));
#endif
this NV is in the preserved range, therefore: */
if (!(U_V(SvNVX(sv) > 0 ? SvNVX(sv) : -SvNVX(sv))
< (UV)IV_MAX)) {
- Perl_croak(aTHX_ "sv_2uv assumed (U_V(fabs(SvNVX(sv))) < (UV)IV_MAX) but SvNVX(sv)=%g U_V is 0x%"UVxf", IV_MAX is 0x%"UVxf"\n", SvNVX(sv), U_V(SvNVX(sv)), (UV)IV_MAX);
+ Perl_croak(aTHX_ "sv_2uv assumed (U_V(fabs(SvNVX(sv))) < (UV)IV_MAX) but SvNVX(sv)=%"NVgf" U_V is 0x%"UVxf", IV_MAX is 0x%"UVxf"\n", SvNVX(sv), U_V(SvNVX(sv)), (UV)IV_MAX);
}
} else
sv_2iuv_non_preserve (sv, numtype);
#else
DEBUG_c({
STORE_NUMERIC_LOCAL_SET_STANDARD();
- PerlIO_printf(Perl_debug_log, "0x%"UVxf" num(%g)\n",
+ PerlIO_printf(Perl_debug_log, "0x%"UVxf" num(%"NVgf")\n",
PTR2UV(sv), SvNVX(sv));
RESTORE_NUMERIC_LOCAL();
});
#else
DEBUG_c({
STORE_NUMERIC_LOCAL_SET_STANDARD();
- PerlIO_printf(Perl_debug_log, "0x%"UVxf" 1nv(%g)\n",
+ PerlIO_printf(Perl_debug_log, "0x%"UVxf" 1nv(%"NVgf")\n",
PTR2UV(sv), SvNVX(sv));
RESTORE_NUMERIC_LOCAL();
});
if (SvROK(sv)) {
SV* tmpsv;
if (SvAMAGIC(sv) && (tmpsv=AMG_CALLun(sv,bool_)) &&
- (SvTYPE(tmpsv) != SVt_RV || (SvRV(tmpsv) != SvRV(sv))))
+ (!SvROK(tmpsv) || (SvRV(tmpsv) != SvRV(sv))))
return SvTRUE(tmpsv);
return SvRV(sv) != 0;
}
}
if (hibit) {
STRLEN len;
-
+
len = SvCUR(sv) + 1; /* Plus the \0 */
SvPVX(sv) = (char*)bytes_to_utf8((U8*)s, &len);
SvCUR(sv) = len - 1;
mg->mg_moremagic = SvMAGIC(sv);
SvMAGIC(sv) = mg;
- /* Some magic contains a reference loop, where the sv and object refer to
- each other. To avoid a reference loop that would prevent such objects
- being freed, we look for such loops and if we find one we avoid
- incrementing the object refcount. */
+ /* Some magic sontains a reference loop, where the sv and object refer to
+ each other. To prevent a reference loop that would prevent such
+ objects being freed, we look for such loops and if we find one we
+ avoid incrementing the object refcount. */
if (!obj || obj == sv ||
how == PERL_MAGIC_arylen ||
how == PERL_MAGIC_qr ||
DEBUG_P(PerlIO_printf(Perl_debug_log,
"Screamer: entering, ptr=%"UVuf", cnt=%ld\n",PTR2UV(ptr),(long)cnt));
DEBUG_P(PerlIO_printf(Perl_debug_log,
- "Screamer: entering: FILE * thinks ptr=%"UVuf", cnt=%ld, base=%"UVuf"\n",
+ "Screamer: entering: PerlIO * thinks ptr=%"UVuf", cnt=%ld, base=%"UVuf"\n",
PTR2UV(PerlIO_get_ptr(fp)), (long)PerlIO_get_cnt(fp),
PTR2UV(PerlIO_has_base(fp) ? PerlIO_get_base(fp) : 0)));
for (;;) {
DEBUG_P(PerlIO_printf(Perl_debug_log,
"Screamer: going to getc, ptr=%"UVuf", cnt=%ld\n",
PTR2UV(ptr),(long)cnt));
- PerlIO_set_ptrcnt(fp, ptr, cnt); /* deregisterize cnt and ptr */
+ PerlIO_set_ptrcnt(fp, (STDCHAR*)ptr, cnt); /* deregisterize cnt and ptr */
+#if 0
DEBUG_P(PerlIO_printf(Perl_debug_log,
"Screamer: pre: FILE * thinks ptr=%"UVuf", cnt=%ld, base=%"UVuf"\n",
PTR2UV(PerlIO_get_ptr(fp)), (long)PerlIO_get_cnt(fp),
PTR2UV(PerlIO_has_base (fp) ? PerlIO_get_base(fp) : 0)));
+#endif
/* This used to call 'filbuf' in stdio form, but as that behaves like
getc when cnt <= 0 we use PerlIO_getc here to avoid introducing
another abstraction. */
i = PerlIO_getc(fp); /* get more characters */
+#if 0
DEBUG_P(PerlIO_printf(Perl_debug_log,
"Screamer: post: FILE * thinks ptr=%"UVuf", cnt=%ld, base=%"UVuf"\n",
PTR2UV(PerlIO_get_ptr(fp)), (long)PerlIO_get_cnt(fp),
PTR2UV(PerlIO_has_base (fp) ? PerlIO_get_base(fp) : 0)));
+#endif
cnt = PerlIO_get_cnt(fp);
ptr = (STDCHAR*)PerlIO_get_ptr(fp); /* reregisterize cnt and ptr */
DEBUG_P(PerlIO_printf(Perl_debug_log,
cnt += shortbuffered;
DEBUG_P(PerlIO_printf(Perl_debug_log,
"Screamer: quitting, ptr=%"UVuf", cnt=%ld\n",PTR2UV(ptr),(long)cnt));
- PerlIO_set_ptrcnt(fp, ptr, cnt); /* put these back or we're in trouble */
+ PerlIO_set_ptrcnt(fp, (STDCHAR*)ptr, cnt); /* put these back or we're in trouble */
DEBUG_P(PerlIO_printf(Perl_debug_log,
"Screamer: end: FILE * thinks ptr=%"UVuf", cnt=%ld, base=%"UVuf"\n",
PTR2UV(PerlIO_get_ptr(fp)), (long)PerlIO_get_cnt(fp),
if (SvGMAGICAL(sv))
mg_get(sv);
if (SvTHINKFIRST(sv)) {
+ if (SvREADONLY(sv) && SvFAKE(sv))
+ sv_force_normal(sv);
if (SvREADONLY(sv)) {
if (PL_curcop != &PL_compiling)
Perl_croak(aTHX_ PL_no_modify);
while (isDIGIT(*d)) d++;
if (*d) {
#ifdef PERL_PRESERVE_IVUV
- /* Got to punt this an an integer if needs be, but we don't issue
+ /* Got to punt this as an integer if needs be, but we don't issue
warnings. Probably ought to make the sv_iv_please() that does
the conversion if possible, and silently. */
int numtype = grok_number(SvPVX(sv), SvCUR(sv), NULL);
DEBUG_c(PerlIO_printf(Perl_debug_log,"sv_inc punt failed to convert '%s' to IOK or NOKp, UV=0x%"UVxf" NV=%"PERL_PRIgldbl"\n",
SvPVX(sv), SvIVX(sv), SvNVX(sv)));
#else
- DEBUG_c(PerlIO_printf(Perl_debug_log,"sv_inc punt failed to convert '%s' to IOK or NOKp, UV=0x%"UVxf" NV=%g\n",
+ DEBUG_c(PerlIO_printf(Perl_debug_log,"sv_inc punt failed to convert '%s' to IOK or NOKp, UV=0x%"UVxf" NV=%"NVgf"\n",
SvPVX(sv), SvIVX(sv), SvNVX(sv)));
#endif
}
if (SvGMAGICAL(sv))
mg_get(sv);
if (SvTHINKFIRST(sv)) {
+ if (SvREADONLY(sv) && SvFAKE(sv))
+ sv_force_normal(sv);
if (SvREADONLY(sv)) {
if (PL_curcop != &PL_compiling)
Perl_croak(aTHX_ PL_no_modify);
DEBUG_c(PerlIO_printf(Perl_debug_log,"sv_dec punt failed to convert '%s' to IOK or NOKp, UV=0x%"UVxf" NV=%"PERL_PRIgldbl"\n",
SvPVX(sv), SvIVX(sv), SvNVX(sv)));
#else
- DEBUG_c(PerlIO_printf(Perl_debug_log,"sv_dec punt failed to convert '%s' to IOK or NOKp, UV=0x%"UVxf" NV=%g\n",
+ DEBUG_c(PerlIO_printf(Perl_debug_log,"sv_dec punt failed to convert '%s' to IOK or NOKp, UV=0x%"UVxf" NV=%"NVgf"\n",
SvPVX(sv), SvIVX(sv), SvNVX(sv)));
#endif
}
mg_set(tmpRef);
-
+
return sv;
}
I32 svix = 0;
static char nullstr[] = "(null)";
SV *argsv = Nullsv;
+ bool has_utf8 = FALSE; /* has the result utf8? */
/* no matter what, this is a string now */
(void)SvPV_force(sv, origlen);
}
}
+ if (!args && svix < svmax && DO_UTF8(*svargs))
+ has_utf8 = TRUE;
+
patend = (char*)pat + patlen;
for (p = (char*)pat; p < patend; p = q) {
bool alt = FALSE;
bool left = FALSE;
bool vectorize = FALSE;
bool vectorarg = FALSE;
- bool vec_utf = FALSE;
+ bool vec_utf8 = FALSE;
char fill = ' ';
char plus = 0;
char intsize = 0;
STRLEN zeros = 0;
bool has_precis = FALSE;
STRLEN precis = 0;
- bool is_utf = FALSE;
+ bool is_utf8 = FALSE; /* is this item utf8? */
char esignbuf[4];
U8 utf8buf[UTF8_MAXLEN+1];
svargs[ewix ? ewix-1 : svix++] : &PL_sv_undef;
dotstr = SvPVx(vecsv, dotstrlen);
if (DO_UTF8(vecsv))
- is_utf = TRUE;
+ is_utf8 = TRUE;
}
if (args) {
vecsv = va_arg(*args, SV*);
vecstr = (U8*)SvPVx(vecsv,veclen);
- vec_utf = DO_UTF8(vecsv);
+ vec_utf8 = DO_UTF8(vecsv);
}
else if (efix ? efix <= svmax : svix < svmax) {
vecsv = svargs[efix ? efix-1 : svix++];
vecstr = (U8*)SvPVx(vecsv,veclen);
- vec_utf = DO_UTF8(vecsv);
+ vec_utf8 = DO_UTF8(vecsv);
}
else {
vecstr = (U8*)"";
&& !IN_BYTES) {
eptr = (char*)utf8buf;
elen = uvchr_to_utf8((U8*)eptr, uv) - utf8buf;
- is_utf = TRUE;
+ is_utf8 = TRUE;
}
else {
c = (char)uv;
if (width) { /* fudge width (can't fudge elen) */
width += elen - sv_len_utf8(argsv);
}
- is_utf = TRUE;
+ is_utf8 = TRUE;
}
}
goto string;
argsv = va_arg(*args, SV*);
eptr = SvPVx(argsv, elen);
if (DO_UTF8(argsv))
- is_utf = TRUE;
+ is_utf8 = TRUE;
string:
vectorize = FALSE;
STRLEN ulen;
if (!veclen)
continue;
- if (vec_utf)
- uv = utf8n_to_uvchr(vecstr, veclen, &ulen, UTF8_ALLOW_ANYUV);
+ if (vec_utf8)
+ uv = utf8n_to_uvchr(vecstr, veclen, &ulen,
+ UTF8_ALLOW_ANYUV);
else {
uv = *vecstr;
ulen = 1;
vector:
if (!veclen)
continue;
- if (vec_utf)
- uv = utf8n_to_uvchr(vecstr, veclen, &ulen, UTF8_ALLOW_ANYUV);
+ if (vec_utf8)
+ uv = utf8n_to_uvchr(vecstr, veclen, &ulen,
+ UTF8_ALLOW_ANYUV);
else {
uv = *vecstr;
ulen = 1;
*p++ = '0';
}
if (elen) {
+ if (is_utf8 != has_utf8) {
+ if (is_utf8) {
+ if (SvCUR(sv)) {
+ sv_utf8_upgrade(sv);
+ p = SvEND(sv);
+ }
+ }
+ else {
+ SV *nsv = sv_2mortal(newSVpvn(eptr, elen));
+ sv_utf8_upgrade(nsv);
+ eptr = SvPVX(nsv);
+ elen = SvCUR(nsv);
+ }
+ }
Copy(eptr, p, elen, char);
p += elen;
}
else
vectorize = FALSE; /* done iterating over vecstr */
}
- if (is_utf)
+ if (is_utf8)
+ has_utf8 = TRUE;
+ if (has_utf8)
SvUTF8_on(sv);
*p = '\0';
SvCUR(sv) = p - SvPVX(sv);
return ret;
/* create anew and remember what it is */
- ret = PerlIO_fdupopen(aTHX_ fp, param);
+ ret = PerlIO_fdupopen(aTHX_ fp, param, PERLIO_DUP_CLONE);
ptr_table_store(PL_ptr_table, fp, ret);
return ret;
}
* their pointers copied. */
IV i;
- CLONE_PARAMS* param = (CLONE_PARAMS*) malloc(sizeof(CLONE_PARAMS));
+ CLONE_PARAMS clone_params;
+ CLONE_PARAMS* param = &clone_params;
PerlInterpreter *my_perl = (PerlInterpreter*)(*ipM->pMalloc)(ipM, sizeof(PerlInterpreter));
PERL_SET_THX(my_perl);
PL_savestack = 0;
PL_retstack = 0;
PL_sig_pending = 0;
+ Zero(&PL_debug_pad, 1, struct perl_debug_pad);
# else /* !DEBUGGING */
Zero(my_perl, 1, PerlInterpreter);
# endif /* DEBUGGING */
PL_Proc = ipP;
#else /* !PERL_IMPLICIT_SYS */
IV i;
- CLONE_PARAMS* param = (CLONE_PARAMS*) malloc(sizeof(CLONE_PARAMS));
+ CLONE_PARAMS clone_params;
+ CLONE_PARAMS* param = &clone_params;
PerlInterpreter *my_perl = (PerlInterpreter*)PerlMem_malloc(sizeof(PerlInterpreter));
PERL_SET_THX(my_perl);
PL_savestack = 0;
PL_retstack = 0;
PL_sig_pending = 0;
+ Zero(&PL_debug_pad, 1, struct perl_debug_pad);
# else /* !DEBUGGING */
Zero(my_perl, 1, PerlInterpreter);
# endif /* DEBUGGING */
}
SvREFCNT_dec(param->stashes);
- Safefree(param);
return my_perl;
}
#endif /* USE_ITHREADS */
/*
+=head1 Unicode Support
+
=for apidoc sv_recode_to_utf8
The encoding is assumed to be an Encode object, on entry the PV