⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dumper.xs

📁 UNIX下perl实现代码
💻 XS
📖 第 1 页 / 共 2 页
字号:
	    totpad = newSVsv(sep);	    sv_catsv(totpad, pad);	    sv_catsv(totpad, apad);	    	    (void)hv_iterinit((HV*)ival);	    i = 0;	    while ((entry = hv_iternext((HV*)ival)))  {		char *nkey;		I32 nticks = 0;				if (i)		    sv_catpvn(retval, ",", 1);		i++;		key = hv_iterkey(entry, &klen);		hval = hv_iterval((HV*)ival, entry);		if (quotekeys || needs_quote(key)) {		    nticks = num_q(key, klen);		    New(0, nkey, klen+nticks+3, char);		    nkey[0] = '\'';		    if (nticks)			klen += esc_q(nkey+1, key, klen);		    else			(void)Copy(key, nkey+1, klen, char);		    nkey[++klen] = '\'';		    nkey[++klen] = '\0';		}		else {		    New(0, nkey, klen, char);		    (void)Copy(key, nkey, klen, char);		}				sname = newSVsv(iname);		sv_catpvn(sname, nkey, klen);		sv_catpvn(sname, "}", 1);		sv_catsv(retval, totpad);		sv_catsv(retval, ipad);		sv_catpvn(retval, nkey, klen);		sv_catpvn(retval, " => ", 4);		if (indent >= 2) {		    char *extra;		    I32 elen = 0;		    newapad = newSVsv(apad);		    New(0, extra, klen+4+1, char);		    while (elen < (klen+4))			extra[elen++] = ' ';		    extra[elen] = '\0';		    sv_catpvn(newapad, extra, elen);		    Safefree(extra);		}		else		    newapad = apad;		DD_dump(aTHX_ hval, SvPVX(sname), SvCUR(sname), retval, seenhv,			postav, levelp,	indent, pad, xpad, newapad, sep,			freezer, toaster, purity, deepcopy, quotekeys, bless,			maxdepth);		SvREFCNT_dec(sname);		Safefree(nkey);		if (indent >= 2)		    SvREFCNT_dec(newapad);	    }	    if (i) {		SV *opad = sv_x(aTHX_ Nullsv, SvPVX(xpad), SvCUR(xpad), *levelp-1);		sv_catsv(retval, totpad);		sv_catsv(retval, opad);		SvREFCNT_dec(opad);	    }	    if (name[0] == '%')		sv_catpvn(retval, ")", 1);	    else		sv_catpvn(retval, "}", 1);	    SvREFCNT_dec(iname);	    SvREFCNT_dec(totpad);	}	else if (realtype == SVt_PVCV) {	    sv_catpvn(retval, "sub { \"DUMMY\" }", 15);	    if (purity)		warn("Encountered CODE ref, using dummy placeholder");	}	else {	    warn("cannot handle ref type %ld", realtype);	}	if (realpack) {  /* free blessed allocs */	    if (indent >= 2) {		SvREFCNT_dec(apad);		apad = blesspad;	    }	    sv_catpvn(retval, ", '", 3);	    sv_catpvn(retval, realpack, strlen(realpack));	    sv_catpvn(retval, "' )", 3);	    if (toaster && SvPOK(toaster) && SvCUR(toaster)) {		sv_catpvn(retval, "->", 2);		sv_catsv(retval, toaster);		sv_catpvn(retval, "()", 2);	    }	}	SvREFCNT_dec(ipad);	(*levelp)--;    }    else {	STRLEN i;		if (namelen) {	    (void) sprintf(id, "0x%lx", (unsigned long)val);	    if ((svp = hv_fetch(seenhv, id, (idlen = strlen(id)), FALSE)) &&		(sv = *svp) && SvROK(sv) &&		(seenentry = (AV*)SvRV(sv)))	    {		SV *othername;		if ((svp = av_fetch(seenentry, 0, FALSE)) && (othername = *svp)		    && (svp = av_fetch(seenentry, 2, FALSE)) && *svp && SvIV(*svp) > 0)		{		    sv_catpvn(retval, "${", 2);		    sv_catsv(retval, othername);		    sv_catpvn(retval, "}", 1);		    return 1;		}	    }	    else {		SV *namesv;		namesv = newSVpvn("\\", 1);		sv_catpvn(namesv, name, namelen);		seenentry = newAV();		av_push(seenentry, namesv);		av_push(seenentry, newRV(val));		(void)hv_store(seenhv, id, strlen(id), newRV((SV*)seenentry), 0);		SvREFCNT_dec(seenentry);	    }	}	if (SvIOK(val)) {            STRLEN len;	    if (SvIsUV(val))	      (void) sprintf(tmpbuf, "%"UVuf, SvUV(val));	    else	      (void) sprintf(tmpbuf, "%"IVdf, SvIV(val));            len = strlen(tmpbuf);	    sv_catpvn(retval, tmpbuf, len);	}	else if (realtype == SVt_PVGV) {/* GLOBs can end up with scribbly names */	    c = SvPV(val, i);	    ++c; --i;			/* just get the name */	    if (i >= 6 && strncmp(c, "main::", 6) == 0) {		c += 4;		i -= 4;	    }	    if (needs_quote(c)) {		sv_grow(retval, SvCUR(retval)+6+2*i);		r = SvPVX(retval)+SvCUR(retval);		r[0] = '*'; r[1] = '{';	r[2] = '\'';		i += esc_q(r+3, c, i);		i += 3;		r[i++] = '\''; r[i++] = '}';		r[i] = '\0';	    }	    else {		sv_grow(retval, SvCUR(retval)+i+2);		r = SvPVX(retval)+SvCUR(retval);		r[0] = '*'; strcpy(r+1, c);		i++;	    }	    SvCUR_set(retval, SvCUR(retval)+i);	    if (purity) {		static char *entries[] = { "{SCALAR}", "{ARRAY}", "{HASH}" };		static STRLEN sizes[] = { 8, 7, 6 };		SV *e;		SV *nname = newSVpvn("", 0);		SV *newapad = newSVpvn("", 0);		GV *gv = (GV*)val;		I32 j;				for (j=0; j<3; j++) {		    e = ((j == 0) ? GvSV(gv) : (j == 1) ? (SV*)GvAV(gv) : (SV*)GvHV(gv));		    if (!e)			continue;		    if (j == 0 && !SvOK(e))			continue;		    {			I32 nlevel = 0;			SV *postentry = newSVpvn(r,i);						sv_setsv(nname, postentry);			sv_catpvn(nname, entries[j], sizes[j]);			sv_catpvn(postentry, " = ", 3);			av_push(postav, postentry);			e = newRV(e);						SvCUR(newapad) = 0;			if (indent >= 2)			    (void)sv_x(aTHX_ newapad, " ", 1, SvCUR(postentry));						DD_dump(aTHX_ e, SvPVX(nname), SvCUR(nname), postentry,				seenhv, postav, &nlevel, indent, pad, xpad,				newapad, sep, freezer, toaster, purity,				deepcopy, quotekeys, bless, maxdepth);			SvREFCNT_dec(e);		    }		}				SvREFCNT_dec(newapad);		SvREFCNT_dec(nname);	    }	}	else if (val == &PL_sv_undef || !SvOK(val)) {	    sv_catpvn(retval, "undef", 5);	}	else {	    c = SvPV(val, i);	    sv_grow(retval, SvCUR(retval)+3+2*i);	    r = SvPVX(retval)+SvCUR(retval);	    r[0] = '\'';	    i += esc_q(r+1, c, i);	    ++i;	    r[i++] = '\'';	    r[i] = '\0';	    SvCUR_set(retval, SvCUR(retval)+i);	}    }    if (idlen) {	if (deepcopy)	    (void)hv_delete(seenhv, id, idlen, G_DISCARD);	else if (namelen && seenentry) {	    SV *mark = *av_fetch(seenentry, 2, TRUE);	    sv_setiv(mark,1);	}    }    return 1;}MODULE = Data::Dumper		PACKAGE = Data::Dumper         PREFIX = Data_Dumper_## This is the exact equivalent of Dump.  Well, almost. The things that are# different as of now (due to Laziness):#   * doesnt do double-quotes yet.#voidData_Dumper_Dumpxs(href, ...)	SV	*href;	PROTOTYPE: $;$$	PPCODE:	{	    HV *hv;	    SV *retval, *valstr;	    HV *seenhv = Nullhv;	    AV *postav, *todumpav, *namesav;	    I32 level = 0;	    I32 indent, terse, useqq, i, imax, postlen;	    SV **svp;	    SV *val, *name, *pad, *xpad, *apad, *sep, *tmp, *varname;	    SV *freezer, *toaster, *bless;	    I32 purity, deepcopy, quotekeys, maxdepth = 0;	    char tmpbuf[1024];	    I32 gimme = GIMME;	    if (!SvROK(href)) {		/* call new to get an object first */		if (items < 2)		    croak("Usage: Data::Dumper::Dumpxs(PACKAGE, VAL_ARY_REF, [NAME_ARY_REF])");				ENTER;		SAVETMPS;				PUSHMARK(sp);		XPUSHs(href);		XPUSHs(sv_2mortal(newSVsv(ST(1))));		if (items >= 3)		    XPUSHs(sv_2mortal(newSVsv(ST(2))));		PUTBACK;		i = perl_call_method("new", G_SCALAR);		SPAGAIN;		if (i)		    href = newSVsv(POPs);		PUTBACK;		FREETMPS;		LEAVE;		if (i)		    (void)sv_2mortal(href);	    }	    todumpav = namesav = Nullav;	    seenhv = Nullhv;	    val = pad = xpad = apad = sep = tmp = varname		= freezer = toaster = bless = &PL_sv_undef;	    name = sv_newmortal();	    indent = 2;	    terse = useqq = purity = deepcopy = 0;	    quotekeys = 1;	    	    retval = newSVpvn("", 0);	    if (SvROK(href)		&& (hv = (HV*)SvRV((SV*)href))		&& SvTYPE(hv) == SVt_PVHV)		{		if ((svp = hv_fetch(hv, "seen", 4, FALSE)) && SvROK(*svp))		    seenhv = (HV*)SvRV(*svp);		if ((svp = hv_fetch(hv, "todump", 6, FALSE)) && SvROK(*svp))		    todumpav = (AV*)SvRV(*svp);		if ((svp = hv_fetch(hv, "names", 5, FALSE)) && SvROK(*svp))		    namesav = (AV*)SvRV(*svp);		if ((svp = hv_fetch(hv, "indent", 6, FALSE)))		    indent = SvIV(*svp);		if ((svp = hv_fetch(hv, "purity", 6, FALSE)))		    purity = SvIV(*svp);		if ((svp = hv_fetch(hv, "terse", 5, FALSE)))		    terse = SvTRUE(*svp);		if ((svp = hv_fetch(hv, "useqq", 5, FALSE)))		    useqq = SvTRUE(*svp);		if ((svp = hv_fetch(hv, "pad", 3, FALSE)))		    pad = *svp;		if ((svp = hv_fetch(hv, "xpad", 4, FALSE)))		    xpad = *svp;		if ((svp = hv_fetch(hv, "apad", 4, FALSE)))		    apad = *svp;		if ((svp = hv_fetch(hv, "sep", 3, FALSE)))		    sep = *svp;		if ((svp = hv_fetch(hv, "varname", 7, FALSE)))		    varname = *svp;		if ((svp = hv_fetch(hv, "freezer", 7, FALSE)))		    freezer = *svp;		if ((svp = hv_fetch(hv, "toaster", 7, FALSE)))		    toaster = *svp;		if ((svp = hv_fetch(hv, "deepcopy", 8, FALSE)))		    deepcopy = SvTRUE(*svp);		if ((svp = hv_fetch(hv, "quotekeys", 9, FALSE)))		    quotekeys = SvTRUE(*svp);		if ((svp = hv_fetch(hv, "bless", 5, FALSE)))		    bless = *svp;		if ((svp = hv_fetch(hv, "maxdepth", 8, FALSE)))		    maxdepth = SvIV(*svp);		postav = newAV();		if (todumpav)		    imax = av_len(todumpav);		else		    imax = -1;		valstr = newSVpvn("",0);		for (i = 0; i <= imax; ++i) {		    SV *newapad;		    		    av_clear(postav);		    if ((svp = av_fetch(todumpav, i, FALSE)))			val = *svp;		    else			val = &PL_sv_undef;		    if ((svp = av_fetch(namesav, i, TRUE)))			sv_setsv(name, *svp);		    else			(void)SvOK_off(name);		    		    if (SvOK(name)) {			if ((SvPVX(name))[0] == '*') {			    if (SvROK(val)) {				switch (SvTYPE(SvRV(val))) {				case SVt_PVAV:				    (SvPVX(name))[0] = '@';				    break;				case SVt_PVHV:				    (SvPVX(name))[0] = '%';				    break;				case SVt_PVCV:				    (SvPVX(name))[0] = '*';				    break;				default:				    (SvPVX(name))[0] = '$';				    break;				}			    }			    else				(SvPVX(name))[0] = '$';			}			else if ((SvPVX(name))[0] != '$')			    sv_insert(name, 0, 0, "$", 1);		    }		    else {			STRLEN nchars = 0;			sv_setpvn(name, "$", 1);			sv_catsv(name, varname);			(void) sprintf(tmpbuf, "%"IVdf, (IV)(i+1));			nchars = strlen(tmpbuf);			sv_catpvn(name, tmpbuf, nchars);		    }		    		    if (indent >= 2) {			SV *tmpsv = sv_x(aTHX_ Nullsv, " ", 1, SvCUR(name)+3);			newapad = newSVsv(apad);			sv_catsv(newapad, tmpsv);			SvREFCNT_dec(tmpsv);		    }		    else			newapad = apad;		    		    DD_dump(aTHX_ val, SvPVX(name), SvCUR(name), valstr, seenhv,			    postav, &level, indent, pad, xpad, newapad, sep,			    freezer, toaster, purity, deepcopy, quotekeys,			    bless, maxdepth);		    		    if (indent >= 2)			SvREFCNT_dec(newapad);		    postlen = av_len(postav);		    if (postlen >= 0 || !terse) {			sv_insert(valstr, 0, 0, " = ", 3);			sv_insert(valstr, 0, 0, SvPVX(name), SvCUR(name));			sv_catpvn(valstr, ";", 1);		    }		    sv_catsv(retval, pad);		    sv_catsv(retval, valstr);		    sv_catsv(retval, sep);		    if (postlen >= 0) {			I32 i;			sv_catsv(retval, pad);			for (i = 0; i <= postlen; ++i) {			    SV *elem;			    svp = av_fetch(postav, i, FALSE);			    if (svp && (elem = *svp)) {				sv_catsv(retval, elem);				if (i < postlen) {				    sv_catpvn(retval, ";", 1);				    sv_catsv(retval, sep);				    sv_catsv(retval, pad);				}			    }			}			sv_catpvn(retval, ";", 1);			    sv_catsv(retval, sep);		    }		    sv_setpvn(valstr, "", 0);		    if (gimme == G_ARRAY) {			XPUSHs(sv_2mortal(retval));			if (i < imax)	/* not the last time thro ? */			    retval = newSVpvn("",0);		    }		}		SvREFCNT_dec(postav);		SvREFCNT_dec(valstr);	    }	    else		croak("Call to new() method failed to return HASH ref");	    if (gimme == G_SCALAR)		XPUSHs(sv_2mortal(retval));	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -