Data-Swap
view release on metacpan or search on metacpan
}
return av;
}
STATIC void install_backrefs(pTHX_ SV *sv, AV *backrefs) {
if (!backrefs)
return;
#if BACKREFS_IN_HV
if (SvTYPE(sv) == SVt_PVHV) {
AV **const avp = Perl_hv_backreferences_p(aTHX_ (HV *) sv);
*avp = backrefs;
return;
}
#endif
sv_magic(sv, (SV *) backrefs, PERL_MAGIC_backref, NULL, 0);
}
STATIC AV *sv_move(pTHX_ SV *dst, SV *src, AV *br)
{
AV *obr = extract_backrefs(aTHX_ src);
#if (PERL_COMBI_VERSION >= 5009003)
dst->sv_u = src->sv_u;
if (SvTYPE(src) == SVt_IV)
SvANY(dst) = (XPVIV *) ((char *) &dst->sv_u.svu_iv
- STRUCT_OFFSET(XPVIV, xiv_iv));
#if (PERL_COMBI_VERSION < 5011000)
else if (SvTYPE(src) == SVt_RV)
SvANY(dst) = &dst->sv_u.svu_rv;
#endif
else
#endif
SvANY(dst) = SvANY(src);
SvFLAGS(dst) = (SvFLAGS(dst) & CONTAINER_FLAGS) |
(SvFLAGS(src) & ~CONTAINER_FLAGS);
install_backrefs(aTHX_ dst, br);
return obr;
}
MODULE = Data::Swap PACKAGE = Data::Swap
PROTOTYPES: DISABLE
BOOT:
CvLVALUE_on(get_cv("Data::Swap::deref", TRUE));
void
deref(...)
PREINIT:
I32 i, n = 0;
I32 sref;
SV *sv;
PPCODE:
sref = (GIMME == G_SCALAR) && (PL_op->op_flags & OPf_REF);
for (i = 0; i < items; i++) {
if (!SvROK(ST(i))) {
STRLEN z;
if (SvOK(ST(i)))
Perl_croak(aTHX_ DA_DEREF_ERR, SvPV(ST(i), z));
if (ckWARN(WARN_UNINITIALIZED))
custom_warn_uninit("deref");
if (sref)
return;
continue;
}
sv = SvRV(ST(i));
if (sref) {
PUSHs(sv);
PUTBACK;
return;
}
switch (SvTYPE(sv)) {
I32 x;
case SVt_PVAV:
if (!(x = av_len((AV *) sv) + 1))
continue;
SP += x;
break;
case SVt_PVHV:
if (!(x = HvKEYS(sv)))
continue;
SP += x * 2;
break;
case SVt_PVCV:
Perl_croak(aTHX_ "Can't deref subroutine reference");
case SVt_PVFM:
Perl_croak(aTHX_ "Can't deref format reference");
case SVt_PVIO:
Perl_croak(aTHX_ "Can't deref filehandle reference");
default:
SP++;
}
ST(n++) = ST(i);
}
EXTEND(SP, 0);
for (i = 0; n--; ) {
SV *sv = SvRV(ST(n));
I32 x = SvTYPE(sv);
if (x == SVt_PVAV) {
i -= x = AvFILL((AV *) sv) + 1;
Copy(AvARRAY((AV *) sv), SP + i + 1, x, SV *);
} else if (x == SVt_PVHV) {
HE *entry;
HV *hv = (HV *) sv;
i -= x = hv_iterinit(hv) * 2;
PUTBACK;
while ((entry = hv_iternext(hv))) {
sv = hv_iterkeysv(entry);
SPAGAIN;
SvREADONLY_on(sv);
SP[++i] = sv;
sv = hv_iterval(hv, entry);
SPAGAIN;
( run in 0.559 second using v1.01-cache-2.11-cpan-71847e10f99 )