1*0Sstevel@tonic-gate typedef char *pvcontents;
2*0Sstevel@tonic-gate typedef char *strconst;
3*0Sstevel@tonic-gate typedef U32 PV;
4*0Sstevel@tonic-gate typedef char *op_tr_array;
5*0Sstevel@tonic-gate typedef int comment_t;
6*0Sstevel@tonic-gate typedef SV *svindex;
7*0Sstevel@tonic-gate typedef OP *opindex;
8*0Sstevel@tonic-gate typedef char *pvindex;
9*0Sstevel@tonic-gate 
10*0Sstevel@tonic-gate #define BGET_FREAD(argp, len, nelem)	\
11*0Sstevel@tonic-gate 	 bl_read(bstate->bs_fdata,(char*)(argp),(len),(nelem))
12*0Sstevel@tonic-gate #define BGET_FGETC() bl_getc(bstate->bs_fdata)
13*0Sstevel@tonic-gate 
14*0Sstevel@tonic-gate /* all this should be made endianness-agnostic */
15*0Sstevel@tonic-gate 
16*0Sstevel@tonic-gate #define BGET_U8(arg)	arg = BGET_FGETC()
17*0Sstevel@tonic-gate #define BGET_U16(arg)	\
18*0Sstevel@tonic-gate 	BGET_FREAD(&arg, sizeof(U16), 1)
19*0Sstevel@tonic-gate #define BGET_U32(arg)	\
20*0Sstevel@tonic-gate 	BGET_FREAD(&arg, sizeof(U32), 1)
21*0Sstevel@tonic-gate #define BGET_UV(arg)	\
22*0Sstevel@tonic-gate 	BGET_FREAD(&arg, sizeof(UV), 1)
23*0Sstevel@tonic-gate #define BGET_PADOFFSET(arg)	\
24*0Sstevel@tonic-gate 	BGET_FREAD(&arg, sizeof(PADOFFSET), 1)
25*0Sstevel@tonic-gate #define BGET_long(arg)		\
26*0Sstevel@tonic-gate 	BGET_FREAD(&arg, sizeof(long), 1)
27*0Sstevel@tonic-gate 
28*0Sstevel@tonic-gate #define BGET_I32(arg)	BGET_U32(arg)
29*0Sstevel@tonic-gate #define BGET_IV(arg)	BGET_UV(arg)
30*0Sstevel@tonic-gate 
31*0Sstevel@tonic-gate #define BGET_PV(arg)	STMT_START {					\
32*0Sstevel@tonic-gate 	BGET_U32(arg);							\
33*0Sstevel@tonic-gate 	if (arg) {							\
34*0Sstevel@tonic-gate 	    New(666, bstate->bs_pv.xpv_pv, arg, char);			\
35*0Sstevel@tonic-gate 	    bl_read(bstate->bs_fdata, bstate->bs_pv.xpv_pv, arg, 1);	\
36*0Sstevel@tonic-gate 	    bstate->bs_pv.xpv_len = arg;				\
37*0Sstevel@tonic-gate 	    bstate->bs_pv.xpv_cur = arg - 1;				\
38*0Sstevel@tonic-gate 	} else {							\
39*0Sstevel@tonic-gate 	    bstate->bs_pv.xpv_pv = 0;					\
40*0Sstevel@tonic-gate 	    bstate->bs_pv.xpv_len = 0;					\
41*0Sstevel@tonic-gate 	    bstate->bs_pv.xpv_cur = 0;					\
42*0Sstevel@tonic-gate 	}								\
43*0Sstevel@tonic-gate     } STMT_END
44*0Sstevel@tonic-gate 
45*0Sstevel@tonic-gate #ifdef BYTELOADER_LOG_COMMENTS
46*0Sstevel@tonic-gate #  define BGET_comment_t(arg) \
47*0Sstevel@tonic-gate     STMT_START {							\
48*0Sstevel@tonic-gate 	char buf[1024];							\
49*0Sstevel@tonic-gate 	int i = 0;							\
50*0Sstevel@tonic-gate 	do {								\
51*0Sstevel@tonic-gate 	    arg = BGET_FGETC();						\
52*0Sstevel@tonic-gate 	    buf[i++] = (char)arg;					\
53*0Sstevel@tonic-gate 	} while (arg != '\n' && arg != EOF);				\
54*0Sstevel@tonic-gate 	buf[i] = '\0';							\
55*0Sstevel@tonic-gate 	PerlIO_printf(PerlIO_stderr(), "%s", buf);			\
56*0Sstevel@tonic-gate     } STMT_END
57*0Sstevel@tonic-gate #else
58*0Sstevel@tonic-gate #  define BGET_comment_t(arg) \
59*0Sstevel@tonic-gate 	do { arg = BGET_FGETC(); } while (arg != '\n' && arg != EOF)
60*0Sstevel@tonic-gate #endif
61*0Sstevel@tonic-gate 
62*0Sstevel@tonic-gate 
63*0Sstevel@tonic-gate #define BGET_op_tr_array(arg) do {			\
64*0Sstevel@tonic-gate 	unsigned short *ary, len;			\
65*0Sstevel@tonic-gate 	BGET_U16(len);					\
66*0Sstevel@tonic-gate 	New(666, ary, len, unsigned short);		\
67*0Sstevel@tonic-gate 	BGET_FREAD(ary, sizeof(unsigned short), len);	\
68*0Sstevel@tonic-gate 	arg = (char *) ary;				\
69*0Sstevel@tonic-gate     } while (0)
70*0Sstevel@tonic-gate 
71*0Sstevel@tonic-gate #define BGET_pvcontents(arg)	arg = bstate->bs_pv.xpv_pv
72*0Sstevel@tonic-gate #define BGET_strconst(arg) STMT_START {	\
73*0Sstevel@tonic-gate 	for (arg = PL_tokenbuf; (*arg = BGET_FGETC()); arg++) /* nothing */; \
74*0Sstevel@tonic-gate 	arg = PL_tokenbuf;			\
75*0Sstevel@tonic-gate     } STMT_END
76*0Sstevel@tonic-gate 
77*0Sstevel@tonic-gate #define BGET_NV(arg) STMT_START {	\
78*0Sstevel@tonic-gate 	char *str;			\
79*0Sstevel@tonic-gate 	BGET_strconst(str);		\
80*0Sstevel@tonic-gate 	arg = Atof(str);		\
81*0Sstevel@tonic-gate     } STMT_END
82*0Sstevel@tonic-gate 
83*0Sstevel@tonic-gate #define BGET_objindex(arg, type) STMT_START {	\
84*0Sstevel@tonic-gate 	BGET_U32(ix);				\
85*0Sstevel@tonic-gate 	arg = (type)bstate->bs_obj_list[ix];	\
86*0Sstevel@tonic-gate     } STMT_END
87*0Sstevel@tonic-gate #define BGET_svindex(arg) BGET_objindex(arg, svindex)
88*0Sstevel@tonic-gate #define BGET_opindex(arg) BGET_objindex(arg, opindex)
89*0Sstevel@tonic-gate #define BGET_pvindex(arg) STMT_START {			\
90*0Sstevel@tonic-gate 	BGET_objindex(arg, pvindex);			\
91*0Sstevel@tonic-gate 	arg = arg ? savepv(arg) : arg;			\
92*0Sstevel@tonic-gate     } STMT_END
93*0Sstevel@tonic-gate 
94*0Sstevel@tonic-gate #define BSET_ldspecsv(sv, arg) sv = specialsv_list[arg]
95*0Sstevel@tonic-gate #define BSET_ldspecsvx(sv, arg) STMT_START {	\
96*0Sstevel@tonic-gate 	BSET_ldspecsv(sv, arg);			\
97*0Sstevel@tonic-gate 	BSET_OBJ_STOREX(sv);			\
98*0Sstevel@tonic-gate     } STMT_END
99*0Sstevel@tonic-gate 
100*0Sstevel@tonic-gate #define BSET_stpv(pv, arg) STMT_START {		\
101*0Sstevel@tonic-gate 	BSET_OBJ_STORE(pv, arg);		\
102*0Sstevel@tonic-gate 	SAVEFREEPV(pv);				\
103*0Sstevel@tonic-gate     } STMT_END
104*0Sstevel@tonic-gate 
105*0Sstevel@tonic-gate #define BSET_sv_refcnt_add(svrefcnt, arg)	svrefcnt += arg
106*0Sstevel@tonic-gate #define BSET_gp_refcnt_add(gprefcnt, arg)	gprefcnt += arg
107*0Sstevel@tonic-gate #define BSET_gp_share(sv, arg) STMT_START {	\
108*0Sstevel@tonic-gate 	gp_free((GV*)sv);			\
109*0Sstevel@tonic-gate 	GvGP(sv) = GvGP(arg);			\
110*0Sstevel@tonic-gate     } STMT_END
111*0Sstevel@tonic-gate 
112*0Sstevel@tonic-gate #define BSET_gv_fetchpv(sv, arg)	sv = (SV*)gv_fetchpv(arg, TRUE, SVt_PV)
113*0Sstevel@tonic-gate #define BSET_gv_fetchpvx(sv, arg) STMT_START {	\
114*0Sstevel@tonic-gate 	BSET_gv_fetchpv(sv, arg);		\
115*0Sstevel@tonic-gate 	BSET_OBJ_STOREX(sv);			\
116*0Sstevel@tonic-gate     } STMT_END
117*0Sstevel@tonic-gate 
118*0Sstevel@tonic-gate #define BSET_gv_stashpv(sv, arg)	sv = (SV*)gv_stashpv(arg, TRUE)
119*0Sstevel@tonic-gate #define BSET_gv_stashpvx(sv, arg) STMT_START {	\
120*0Sstevel@tonic-gate 	BSET_gv_stashpv(sv, arg);		\
121*0Sstevel@tonic-gate 	BSET_OBJ_STOREX(sv);			\
122*0Sstevel@tonic-gate     } STMT_END
123*0Sstevel@tonic-gate 
124*0Sstevel@tonic-gate #define BSET_sv_magic(sv, arg)		sv_magic(sv, Nullsv, arg, 0, 0)
125*0Sstevel@tonic-gate #define BSET_mg_name(mg, arg)	mg->mg_ptr = arg; mg->mg_len = bstate->bs_pv.xpv_cur
126*0Sstevel@tonic-gate #define BSET_mg_namex(mg, arg)			\
127*0Sstevel@tonic-gate 	(mg->mg_ptr = (char*)SvREFCNT_inc((SV*)arg),	\
128*0Sstevel@tonic-gate 	 mg->mg_len = HEf_SVKEY)
129*0Sstevel@tonic-gate #define BSET_sv_upgrade(sv, arg)	(void)SvUPGRADE(sv, arg)
130*0Sstevel@tonic-gate #define BSET_xpv(sv)	do {	\
131*0Sstevel@tonic-gate 	SvPV_set(sv, bstate->bs_pv.xpv_pv);	\
132*0Sstevel@tonic-gate 	SvCUR_set(sv, bstate->bs_pv.xpv_cur);	\
133*0Sstevel@tonic-gate 	SvLEN_set(sv, bstate->bs_pv.xpv_len);	\
134*0Sstevel@tonic-gate     } while (0)
135*0Sstevel@tonic-gate #define BSET_av_extend(sv, arg)	av_extend((AV*)sv, arg)
136*0Sstevel@tonic-gate 
137*0Sstevel@tonic-gate #define BSET_av_push(sv, arg)	av_push((AV*)sv, arg)
138*0Sstevel@tonic-gate #define BSET_av_pushx(sv, arg)	(AvARRAY(sv)[++AvFILLp(sv)] = arg)
139*0Sstevel@tonic-gate #define BSET_hv_store(sv, arg)	\
140*0Sstevel@tonic-gate 	hv_store((HV*)sv, bstate->bs_pv.xpv_pv, bstate->bs_pv.xpv_cur, arg, 0)
141*0Sstevel@tonic-gate #define BSET_pv_free(pv)	Safefree(pv.xpv_pv)
142*0Sstevel@tonic-gate 
143*0Sstevel@tonic-gate 
144*0Sstevel@tonic-gate #ifdef USE_ITHREADS
145*0Sstevel@tonic-gate 
146*0Sstevel@tonic-gate /* copied after the code in newPMOP() */
147*0Sstevel@tonic-gate #define BSET_pregcomp(o, arg) \
148*0Sstevel@tonic-gate     STMT_START { \
149*0Sstevel@tonic-gate         SV* repointer; \
150*0Sstevel@tonic-gate 	REGEXP* rx = arg ? \
151*0Sstevel@tonic-gate 	    CALLREGCOMP(aTHX_ arg, arg + bstate->bs_pv.xpv_cur, cPMOPx(o)) : \
152*0Sstevel@tonic-gate 	    Null(REGEXP*); \
153*0Sstevel@tonic-gate         if(av_len((AV*) PL_regex_pad[0]) > -1) { \
154*0Sstevel@tonic-gate             repointer = av_pop((AV*)PL_regex_pad[0]); \
155*0Sstevel@tonic-gate             cPMOPx(o)->op_pmoffset = SvIV(repointer); \
156*0Sstevel@tonic-gate             SvREPADTMP_off(repointer); \
157*0Sstevel@tonic-gate             sv_setiv(repointer,PTR2IV(rx)); \
158*0Sstevel@tonic-gate         } else { \
159*0Sstevel@tonic-gate             repointer = newSViv(PTR2IV(rx)); \
160*0Sstevel@tonic-gate             av_push(PL_regex_padav,SvREFCNT_inc(repointer)); \
161*0Sstevel@tonic-gate             cPMOPx(o)->op_pmoffset = av_len(PL_regex_padav); \
162*0Sstevel@tonic-gate             PL_regex_pad = AvARRAY(PL_regex_padav); \
163*0Sstevel@tonic-gate         } \
164*0Sstevel@tonic-gate     } STMT_END
165*0Sstevel@tonic-gate 
166*0Sstevel@tonic-gate #else
167*0Sstevel@tonic-gate #define BSET_pregcomp(o, arg) \
168*0Sstevel@tonic-gate     STMT_START { \
169*0Sstevel@tonic-gate 	PM_SETRE(((PMOP*)o), (arg ? \
170*0Sstevel@tonic-gate 	     CALLREGCOMP(aTHX_ arg, arg + bstate->bs_pv.xpv_cur, cPMOPx(o)): \
171*0Sstevel@tonic-gate 	     Null(REGEXP*))); \
172*0Sstevel@tonic-gate     } STMT_END
173*0Sstevel@tonic-gate 
174*0Sstevel@tonic-gate #endif /* USE_THREADS */
175*0Sstevel@tonic-gate 
176*0Sstevel@tonic-gate 
177*0Sstevel@tonic-gate #define BSET_newsv(sv, arg)				\
178*0Sstevel@tonic-gate 	    switch(arg) {				\
179*0Sstevel@tonic-gate 	    case SVt_PVAV:				\
180*0Sstevel@tonic-gate 		sv = (SV*)newAV();			\
181*0Sstevel@tonic-gate 		break;					\
182*0Sstevel@tonic-gate 	    case SVt_PVHV:				\
183*0Sstevel@tonic-gate 		sv = (SV*)newHV();			\
184*0Sstevel@tonic-gate 		break;					\
185*0Sstevel@tonic-gate 	    default:					\
186*0Sstevel@tonic-gate 		sv = NEWSV(0,0);			\
187*0Sstevel@tonic-gate 		SvUPGRADE(sv, (arg));			\
188*0Sstevel@tonic-gate 	    }
189*0Sstevel@tonic-gate #define BSET_newsvx(sv, arg) STMT_START {		\
190*0Sstevel@tonic-gate 	    BSET_newsv(sv, arg &  SVTYPEMASK);		\
191*0Sstevel@tonic-gate 	    SvFLAGS(sv) = arg;				\
192*0Sstevel@tonic-gate 	    BSET_OBJ_STOREX(sv);			\
193*0Sstevel@tonic-gate 	} STMT_END
194*0Sstevel@tonic-gate 
195*0Sstevel@tonic-gate #define BSET_newop(o, arg)	NewOpSz(666, o, arg)
196*0Sstevel@tonic-gate #define BSET_newopx(o, arg) STMT_START {	\
197*0Sstevel@tonic-gate 	register int sz = arg & 0x7f;		\
198*0Sstevel@tonic-gate 	register OP* newop;			\
199*0Sstevel@tonic-gate 	BSET_newop(newop, sz);			\
200*0Sstevel@tonic-gate 	/* newop->op_next = o; XXX */		\
201*0Sstevel@tonic-gate 	o = newop;				\
202*0Sstevel@tonic-gate 	arg >>=7;				\
203*0Sstevel@tonic-gate 	BSET_op_type(o, arg);			\
204*0Sstevel@tonic-gate 	BSET_OBJ_STOREX(o);			\
205*0Sstevel@tonic-gate     } STMT_END
206*0Sstevel@tonic-gate 
207*0Sstevel@tonic-gate #define BSET_newopn(o, arg) STMT_START {	\
208*0Sstevel@tonic-gate 	OP *oldop = o;				\
209*0Sstevel@tonic-gate 	BSET_newop(o, arg);			\
210*0Sstevel@tonic-gate 	oldop->op_next = o;			\
211*0Sstevel@tonic-gate     } STMT_END
212*0Sstevel@tonic-gate 
213*0Sstevel@tonic-gate #define BSET_ret(foo) STMT_START {		\
214*0Sstevel@tonic-gate 	Safefree(bstate->bs_obj_list);		\
215*0Sstevel@tonic-gate 	return 0;				\
216*0Sstevel@tonic-gate     } STMT_END
217*0Sstevel@tonic-gate 
218*0Sstevel@tonic-gate #define BSET_op_pmstashpv(op, arg)	PmopSTASHPV_set(op, arg)
219*0Sstevel@tonic-gate 
220*0Sstevel@tonic-gate /*
221*0Sstevel@tonic-gate  * stolen from toke.c: better if that was a function.
222*0Sstevel@tonic-gate  * in toke.c there are also #ifdefs for dosish systems and i/o layers
223*0Sstevel@tonic-gate  */
224*0Sstevel@tonic-gate 
225*0Sstevel@tonic-gate #if defined(HAS_FCNTL) && defined(F_SETFD)
226*0Sstevel@tonic-gate #define set_clonex(fp)				\
227*0Sstevel@tonic-gate 	STMT_START {				\
228*0Sstevel@tonic-gate 	    int fd = PerlIO_fileno(fp);		\
229*0Sstevel@tonic-gate 	    fcntl(fd,F_SETFD,fd >= 3);		\
230*0Sstevel@tonic-gate 	} STMT_END
231*0Sstevel@tonic-gate #else
232*0Sstevel@tonic-gate #define set_clonex(fp)
233*0Sstevel@tonic-gate #endif
234*0Sstevel@tonic-gate 
235*0Sstevel@tonic-gate #define BSET_data(dummy,arg)						\
236*0Sstevel@tonic-gate     STMT_START {							\
237*0Sstevel@tonic-gate 	GV *gv;								\
238*0Sstevel@tonic-gate 	char *pname = "main";						\
239*0Sstevel@tonic-gate 	if (arg == 'D')							\
240*0Sstevel@tonic-gate 	    pname = HvNAME(PL_curstash ? PL_curstash : PL_defstash);	\
241*0Sstevel@tonic-gate 	gv = gv_fetchpv(Perl_form(aTHX_ "%s::DATA", pname), TRUE, SVt_PVIO);\
242*0Sstevel@tonic-gate 	GvMULTI_on(gv);							\
243*0Sstevel@tonic-gate 	if (!GvIO(gv))							\
244*0Sstevel@tonic-gate 	    GvIOp(gv) = newIO();					\
245*0Sstevel@tonic-gate 	IoIFP(GvIOp(gv)) = PL_rsfp;					\
246*0Sstevel@tonic-gate 	set_clonex(PL_rsfp);						\
247*0Sstevel@tonic-gate 	/* Mark this internal pseudo-handle as clean */			\
248*0Sstevel@tonic-gate 	IoFLAGS(GvIOp(gv)) |= IOf_UNTAINT;				\
249*0Sstevel@tonic-gate 	if (PL_preprocess)						\
250*0Sstevel@tonic-gate 	    IoTYPE(GvIOp(gv)) = IoTYPE_PIPE;				\
251*0Sstevel@tonic-gate 	else if ((PerlIO*)PL_rsfp == PerlIO_stdin())			\
252*0Sstevel@tonic-gate 	    IoTYPE(GvIOp(gv)) = IoTYPE_STD;				\
253*0Sstevel@tonic-gate 	else								\
254*0Sstevel@tonic-gate 	    IoTYPE(GvIOp(gv)) = IoTYPE_RDONLY;				\
255*0Sstevel@tonic-gate 	Safefree(bstate->bs_obj_list);					\
256*0Sstevel@tonic-gate 	return 1;							\
257*0Sstevel@tonic-gate     } STMT_END
258*0Sstevel@tonic-gate 
259*0Sstevel@tonic-gate /* stolen from op.c */
260*0Sstevel@tonic-gate #define BSET_load_glob(foo, gv)						\
261*0Sstevel@tonic-gate     STMT_START {							\
262*0Sstevel@tonic-gate         GV *glob_gv;							\
263*0Sstevel@tonic-gate         ENTER;								\
264*0Sstevel@tonic-gate         Perl_load_module(aTHX_ PERL_LOADMOD_NOIMPORT,			\
265*0Sstevel@tonic-gate                 newSVpvn("File::Glob", 10), Nullsv, Nullsv, Nullsv);	\
266*0Sstevel@tonic-gate         glob_gv = gv_fetchpv("File::Glob::csh_glob", FALSE, SVt_PVCV);	\
267*0Sstevel@tonic-gate         GvCV(gv) = GvCV(glob_gv);					\
268*0Sstevel@tonic-gate         SvREFCNT_inc((SV*)GvCV(gv));					\
269*0Sstevel@tonic-gate         GvIMPORTED_CV_on(gv);						\
270*0Sstevel@tonic-gate         LEAVE;								\
271*0Sstevel@tonic-gate     } STMT_END
272*0Sstevel@tonic-gate 
273*0Sstevel@tonic-gate /*
274*0Sstevel@tonic-gate  * Kludge special-case workaround for OP_MAPSTART
275*0Sstevel@tonic-gate  * which needs the ppaddr for OP_GREPSTART. Blech.
276*0Sstevel@tonic-gate  */
277*0Sstevel@tonic-gate #define BSET_op_type(o, arg) STMT_START {	\
278*0Sstevel@tonic-gate 	o->op_type = arg;			\
279*0Sstevel@tonic-gate 	if (arg == OP_MAPSTART)			\
280*0Sstevel@tonic-gate 	    arg = OP_GREPSTART;			\
281*0Sstevel@tonic-gate 	o->op_ppaddr = PL_ppaddr[arg];		\
282*0Sstevel@tonic-gate     } STMT_END
283*0Sstevel@tonic-gate #define BSET_op_ppaddr(o, arg) Perl_croak(aTHX_ "op_ppaddr not yet implemented")
284*0Sstevel@tonic-gate #define BSET_curpad(pad, arg) STMT_START {	\
285*0Sstevel@tonic-gate 	PL_comppad = (AV *)arg;			\
286*0Sstevel@tonic-gate 	pad = AvARRAY(arg);			\
287*0Sstevel@tonic-gate     } STMT_END
288*0Sstevel@tonic-gate 
289*0Sstevel@tonic-gate #ifdef USE_ITHREADS
290*0Sstevel@tonic-gate #define BSET_cop_file(cop, arg)		CopFILE_set(cop,arg)
291*0Sstevel@tonic-gate #define BSET_cop_stashpv(cop, arg)	CopSTASHPV_set(cop,arg)
292*0Sstevel@tonic-gate #else
293*0Sstevel@tonic-gate /* this works now that Sarathy's changed the CopFILE_set macro to do the SvREFCNT_inc()
294*0Sstevel@tonic-gate 	-- BKS 6-2-2000 */
295*0Sstevel@tonic-gate /* that really meant the actual CopFILEGV_set */
296*0Sstevel@tonic-gate #define BSET_cop_filegv(cop, arg)	CopFILEGV_set(cop,arg)
297*0Sstevel@tonic-gate #define BSET_cop_stash(cop,arg)		CopSTASH_set(cop,(HV*)arg)
298*0Sstevel@tonic-gate #endif
299*0Sstevel@tonic-gate 
300*0Sstevel@tonic-gate /* this is simply stolen from the code in newATTRSUB() */
301*0Sstevel@tonic-gate #define BSET_push_begin(ary,cv)				\
302*0Sstevel@tonic-gate 	STMT_START {					\
303*0Sstevel@tonic-gate             I32 oldscope = PL_scopestack_ix;		\
304*0Sstevel@tonic-gate             ENTER;					\
305*0Sstevel@tonic-gate             SAVECOPFILE(&PL_compiling);			\
306*0Sstevel@tonic-gate             SAVECOPLINE(&PL_compiling);			\
307*0Sstevel@tonic-gate             if (!PL_beginav)				\
308*0Sstevel@tonic-gate                 PL_beginav = newAV();			\
309*0Sstevel@tonic-gate             av_push(PL_beginav, (SV*)cv);		\
310*0Sstevel@tonic-gate 	    GvCV(CvGV(cv)) = 0;               /* cv has been hijacked */\
311*0Sstevel@tonic-gate             call_list(oldscope, PL_beginav);		\
312*0Sstevel@tonic-gate             PL_curcop = &PL_compiling;			\
313*0Sstevel@tonic-gate             PL_compiling.op_private = (U8)(PL_hints & HINT_PRIVATE_MASK);\
314*0Sstevel@tonic-gate             LEAVE;					\
315*0Sstevel@tonic-gate 	} STMT_END
316*0Sstevel@tonic-gate #define BSET_push_init(ary,cv)				\
317*0Sstevel@tonic-gate 	STMT_START {					\
318*0Sstevel@tonic-gate 	    av_unshift((PL_initav ? PL_initav : 	\
319*0Sstevel@tonic-gate 		(PL_initav = newAV(), PL_initav)), 1); 	\
320*0Sstevel@tonic-gate 	    av_store(PL_initav, 0, cv);			\
321*0Sstevel@tonic-gate 	} STMT_END
322*0Sstevel@tonic-gate #define BSET_push_end(ary,cv)				\
323*0Sstevel@tonic-gate 	STMT_START {					\
324*0Sstevel@tonic-gate 	    av_unshift((PL_endav ? PL_endav : 		\
325*0Sstevel@tonic-gate 	    (PL_endav = newAV(), PL_endav)), 1);	\
326*0Sstevel@tonic-gate 	    av_store(PL_endav, 0, cv);			\
327*0Sstevel@tonic-gate 	} STMT_END
328*0Sstevel@tonic-gate #define BSET_OBJ_STORE(obj, ix)			\
329*0Sstevel@tonic-gate 	((I32)ix > bstate->bs_obj_list_fill ?	\
330*0Sstevel@tonic-gate 	 bset_obj_store(aTHX_ bstate, obj, (I32)ix) : \
331*0Sstevel@tonic-gate 	 (bstate->bs_obj_list[ix] = obj),	\
332*0Sstevel@tonic-gate 	 bstate->bs_ix = ix+1)
333*0Sstevel@tonic-gate #define BSET_OBJ_STOREX(obj)			\
334*0Sstevel@tonic-gate 	(bstate->bs_ix > bstate->bs_obj_list_fill ?	\
335*0Sstevel@tonic-gate 	 bset_obj_store(aTHX_ bstate, obj, bstate->bs_ix) : \
336*0Sstevel@tonic-gate 	 (bstate->bs_obj_list[bstate->bs_ix] = obj),	\
337*0Sstevel@tonic-gate 	 bstate->bs_ix++)
338*0Sstevel@tonic-gate 
339*0Sstevel@tonic-gate #define BSET_signal(cv, name)						\
340*0Sstevel@tonic-gate 	mg_set(*hv_store(GvHV(gv_fetchpv("SIG", TRUE, SVt_PVHV)),	\
341*0Sstevel@tonic-gate 		name, strlen(name), cv, 0))
342*0Sstevel@tonic-gate 
343*0Sstevel@tonic-gate /* NOTE: the bytecode header only sanity-checks the bytecode. If a script cares about
344*0Sstevel@tonic-gate  * what version of Perl it's being called under, it should do a 'use 5.006_001' or
345*0Sstevel@tonic-gate  * equivalent. However, since the header includes checks requiring an exact match in
346*0Sstevel@tonic-gate  * ByteLoader versions (we can't guarantee forward compatibility), you don't
347*0Sstevel@tonic-gate  * need to specify one:
348*0Sstevel@tonic-gate  * 	use ByteLoader;
349*0Sstevel@tonic-gate  * is all you need.
350*0Sstevel@tonic-gate  *	-- BKS, June 2000
351*0Sstevel@tonic-gate */
352*0Sstevel@tonic-gate 
353*0Sstevel@tonic-gate #define HEADER_FAIL(f)	\
354*0Sstevel@tonic-gate 	Perl_croak(aTHX_ "Invalid bytecode for this architecture: " f)
355*0Sstevel@tonic-gate #define HEADER_FAIL1(f, arg1)	\
356*0Sstevel@tonic-gate 	Perl_croak(aTHX_ "Invalid bytecode for this architecture: " f, arg1)
357*0Sstevel@tonic-gate #define HEADER_FAIL2(f, arg1, arg2)	\
358*0Sstevel@tonic-gate 	Perl_croak(aTHX_ "Invalid bytecode for this architecture: " f, arg1, arg2)
359*0Sstevel@tonic-gate 
360*0Sstevel@tonic-gate #define BYTECODE_HEADER_CHECK					\
361*0Sstevel@tonic-gate 	STMT_START {						\
362*0Sstevel@tonic-gate 	    U32 sz = 0;						\
363*0Sstevel@tonic-gate 	    strconst str;					\
364*0Sstevel@tonic-gate 								\
365*0Sstevel@tonic-gate 	    BGET_U32(sz); /* Magic: 'PLBC' */			\
366*0Sstevel@tonic-gate 	    if (sz != 0x43424c50) {				\
367*0Sstevel@tonic-gate 		HEADER_FAIL1("bad magic (want 0x43424c50, got %#x)", (int)sz);		\
368*0Sstevel@tonic-gate 	    }							\
369*0Sstevel@tonic-gate 	    BGET_strconst(str);	/* archname */			\
370*0Sstevel@tonic-gate 	    if (strNE(str, ARCHNAME)) {				\
371*0Sstevel@tonic-gate 		HEADER_FAIL2("wrong architecture (want %s, you have %s)",str,ARCHNAME);	\
372*0Sstevel@tonic-gate 	    }							\
373*0Sstevel@tonic-gate 	    BGET_strconst(str); /* ByteLoader version */	\
374*0Sstevel@tonic-gate 	    if (strNE(str, VERSION)) {				\
375*0Sstevel@tonic-gate 		HEADER_FAIL2("mismatched ByteLoader versions (want %s, you have %s)",	\
376*0Sstevel@tonic-gate 			str, VERSION);				\
377*0Sstevel@tonic-gate 	    }							\
378*0Sstevel@tonic-gate 	    BGET_U32(sz); /* ivsize */				\
379*0Sstevel@tonic-gate 	    if (sz != IVSIZE) {					\
380*0Sstevel@tonic-gate 		HEADER_FAIL("different IVSIZE");		\
381*0Sstevel@tonic-gate 	    }							\
382*0Sstevel@tonic-gate 	    BGET_U32(sz); /* ptrsize */				\
383*0Sstevel@tonic-gate 	    if (sz != PTRSIZE) {				\
384*0Sstevel@tonic-gate 		HEADER_FAIL("different PTRSIZE");		\
385*0Sstevel@tonic-gate 	    }							\
386*0Sstevel@tonic-gate 	} STMT_END
387