This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
perl 5.0 alpha 2
[perl5.git] / mg.c
CommitLineData
79072805
LW
1/* $RCSfile: hash.c,v $$Revision: 4.1 $$Date: 92/08/07 18:21:48 $
2 *
3 * Copyright (c) 1993, Larry Wall
4 *
5 * You may distribute under the terms of either the GNU General Public
6 * License or the Artistic License, as specified in the README file.
7 *
8 * $Log: hash.c,v $
9 */
10
11#include "EXTERN.h"
12#include "perl.h"
13
14int
15mg_get(sv)
16SV* sv;
17{
18 MAGIC* mg;
19 for (mg = SvMAGIC(sv); mg; mg = mg->mg_moremagic) {
20 MGVTBL* vtbl = mg->mg_virtual;
21 if (vtbl && vtbl->svt_get)
22 (*vtbl->svt_get)(sv, mg);
23 }
24 return 0;
25}
26
27int
28mg_set(sv)
29SV* sv;
30{
31 MAGIC* mg;
32 for (mg = SvMAGIC(sv); mg; mg = mg->mg_moremagic) {
33 MGVTBL* vtbl = mg->mg_virtual;
34 if (vtbl && vtbl->svt_set)
35 (*vtbl->svt_set)(sv, mg);
36 }
37 return 0;
38}
39
40U32
41mg_len(sv)
42SV* sv;
43{
44 MAGIC* mg;
45 for (mg = SvMAGIC(sv); mg; mg = mg->mg_moremagic) {
46 MGVTBL* vtbl = mg->mg_virtual;
47 if (vtbl && vtbl->svt_len)
48 return (*vtbl->svt_len)(sv, mg);
49 }
50 if (!SvPOK(sv) && SvNIOK(sv))
51 sv_2pv(sv);
52 if (SvPOK(sv))
53 return SvCUR(sv);
54 return 0;
55}
56
57int
58mg_clear(sv)
59SV* sv;
60{
61 MAGIC* mg;
62 for (mg = SvMAGIC(sv); mg; mg = mg->mg_moremagic) {
63 MGVTBL* vtbl = mg->mg_virtual;
64 if (vtbl && vtbl->svt_clear)
65 (*vtbl->svt_clear)(sv, mg);
66 }
67 return 0;
68}
69
70int
71mg_free(sv, type)
72SV* sv;
73char type;
74{
75 MAGIC* mg;
76 MAGIC** mgp = &SvMAGIC(sv);
77 for (mg = *mgp; mg; mg = *mgp) {
78 if (mg->mg_type == type) {
79 MGVTBL* vtbl = mg->mg_virtual;
80 *mgp = mg->mg_moremagic;
81 if (vtbl && vtbl->svt_free)
82 (*vtbl->svt_free)(sv, mg);
83 if (mg->mg_ptr)
84 Safefree(mg->mg_ptr);
85 Safefree(mg);
86 }
87 else
88 mgp = &mg->mg_moremagic;
89 }
90 return 0;
91}
92
93int
94mg_freeall(sv)
95SV* sv;
96{
97 MAGIC* mg;
98 MAGIC* moremagic;
99 for (mg = SvMAGIC(sv); mg; mg = moremagic) {
100 MGVTBL* vtbl = mg->mg_virtual;
101 moremagic = mg->mg_moremagic;
102 if (vtbl && vtbl->svt_free)
103 (*vtbl->svt_free)(sv, mg);
104 if (mg->mg_ptr)
105 Safefree(mg->mg_ptr);
106 Safefree(mg);
107 }
108 SvMAGIC(sv) = 0;
109 return 0;
110}
111
112#if !defined(NSIG) || defined(M_UNIX) || defined(M_XENIX)
113#include <signal.h>
114#endif
115
116#ifdef VOIDSIG
117#define handlertype void
118#else
119#define handlertype int
120#endif
121
122static handlertype sighandler();
123
124int
125magic_get(sv, mg)
126SV *sv;
127MAGIC *mg;
128{
129 register I32 paren;
130 register char *s;
131 register I32 i;
132
133 switch (*mg->mg_ptr) {
134 case '\004': /* ^D */
135 sv_setiv(sv,(I32)(debug & 32767));
136 break;
137 case '\006': /* ^F */
138 sv_setiv(sv,(I32)maxsysfd);
139 break;
140 case '\t': /* ^I */
141 if (inplace)
142 sv_setpv(sv, inplace);
143 else
144 sv_setsv(sv,&sv_undef);
145 break;
146 case '\020': /* ^P */
147 sv_setiv(sv,(I32)perldb);
148 break;
149 case '\024': /* ^T */
150 sv_setiv(sv,(I32)basetime);
151 break;
152 case '\027': /* ^W */
153 sv_setiv(sv,(I32)dowarn);
154 break;
155 case '1': case '2': case '3': case '4':
156 case '5': case '6': case '7': case '8': case '9': case '&':
157 if (curpm) {
158 paren = atoi(GvENAME(mg->mg_obj));
159 getparen:
160 if (curpm->op_pmregexp &&
161 paren <= curpm->op_pmregexp->nparens &&
162 (s = curpm->op_pmregexp->startp[paren]) ) {
163 i = curpm->op_pmregexp->endp[paren] - s;
164 if (i >= 0)
165 sv_setpvn(sv,s,i);
166 else
167 sv_setsv(sv,&sv_undef);
168 }
169 else
170 sv_setsv(sv,&sv_undef);
171 }
172 break;
173 case '+':
174 if (curpm) {
175 paren = curpm->op_pmregexp->lastparen;
176 goto getparen;
177 }
178 break;
179 case '`':
180 if (curpm) {
181 if (curpm->op_pmregexp &&
182 (s = curpm->op_pmregexp->subbeg) ) {
183 i = curpm->op_pmregexp->startp[0] - s;
184 if (i >= 0)
185 sv_setpvn(sv,s,i);
186 else
187 sv_setpvn(sv,"",0);
188 }
189 else
190 sv_setpvn(sv,"",0);
191 }
192 break;
193 case '\'':
194 if (curpm) {
195 if (curpm->op_pmregexp &&
196 (s = curpm->op_pmregexp->endp[0]) ) {
197 sv_setpvn(sv,s, curpm->op_pmregexp->subend - s);
198 }
199 else
200 sv_setpvn(sv,"",0);
201 }
202 break;
203 case '.':
204#ifndef lint
205 if (last_in_gv && GvIO(last_in_gv)) {
206 sv_setiv(sv,(I32)GvIO(last_in_gv)->lines);
207 }
208#endif
209 break;
210 case '?':
211 sv_setiv(sv,(I32)statusvalue);
212 break;
213 case '^':
214 s = GvIO(defoutgv)->top_name;
215 if (s)
216 sv_setpv(sv,s);
217 else {
218 sv_setpv(sv,GvENAME(defoutgv));
219 sv_catpv(sv,"_TOP");
220 }
221 break;
222 case '~':
223 s = GvIO(defoutgv)->fmt_name;
224 if (!s)
225 s = GvENAME(defoutgv);
226 sv_setpv(sv,s);
227 break;
228#ifndef lint
229 case '=':
230 sv_setiv(sv,(I32)GvIO(defoutgv)->page_len);
231 break;
232 case '-':
233 sv_setiv(sv,(I32)GvIO(defoutgv)->lines_left);
234 break;
235 case '%':
236 sv_setiv(sv,(I32)GvIO(defoutgv)->page);
237 break;
238#endif
239 case ':':
240 break;
241 case '/':
242 break;
243 case '[':
244 sv_setiv(sv,(I32)arybase);
245 break;
246 case '|':
247 if (!GvIO(defoutgv))
248 GvIO(defoutgv) = newIO();
249 sv_setiv(sv, (GvIO(defoutgv)->flags & IOf_FLUSH) != 0 );
250 break;
251 case ',':
252 sv_setpvn(sv,ofs,ofslen);
253 break;
254 case '\\':
255 sv_setpvn(sv,ors,orslen);
256 break;
257 case '#':
258 sv_setpv(sv,ofmt);
259 break;
260 case '!':
261 sv_setnv(sv,(double)errno);
262 sv_setpv(sv, errno ? strerror(errno) : "");
263 SvNOK_on(sv); /* what a wonderful hack! */
264 break;
265 case '<':
266 sv_setiv(sv,(I32)uid);
267 break;
268 case '>':
269 sv_setiv(sv,(I32)euid);
270 break;
271 case '(':
272 s = buf;
273 (void)sprintf(s,"%d",(int)gid);
274 goto add_groups;
275 case ')':
276 s = buf;
277 (void)sprintf(s,"%d",(int)egid);
278 add_groups:
279 while (*s) s++;
280#ifdef HAS_GETGROUPS
281#ifndef NGROUPS
282#define NGROUPS 32
283#endif
284 {
285 GROUPSTYPE gary[NGROUPS];
286
287 i = getgroups(NGROUPS,gary);
288 while (--i >= 0) {
289 (void)sprintf(s," %ld", (long)gary[i]);
290 while (*s) s++;
291 }
292 }
293#endif
294 sv_setpv(sv,buf);
295 break;
296 case '*':
297 break;
298 case '0':
299 break;
300 }
301}
302
303int
304magic_getuvar(sv, mg)
305SV *sv;
306MAGIC *mg;
307{
308 struct ufuncs *uf = (struct ufuncs *)mg->mg_ptr;
309
310 if (uf && uf->uf_val)
311 (*uf->uf_val)(uf->uf_index, sv);
312 return 0;
313}
314
315int
316magic_setenv(sv,mg)
317SV* sv;
318MAGIC* mg;
319{
320 register char *s;
321 I32 i;
322 s = SvPV(sv);
323 my_setenv(mg->mg_ptr,s);
324 /* And you'll never guess what the dog had */
325 /* in its mouth... */
326#ifdef TAINT
327 if (s && strEQ(mg->mg_ptr,"PATH")) {
328 char *strend = SvEND(sv);
329
330 while (s < strend) {
331 s = cpytill(tokenbuf,s,strend,':',&i);
332 s++;
333 if (*tokenbuf != '/'
334 || (stat(tokenbuf,&statbuf) && (statbuf.st_mode & 2)) )
335 sv->sv_tainted = 2;
336 }
337 }
338#endif
339 return 0;
340}
341
342int
343magic_setsig(sv,mg)
344SV* sv;
345MAGIC* mg;
346{
347 register char *s;
348 I32 i;
349 s = SvPV(sv);
350 i = whichsig(mg->mg_ptr); /* ...no, a brick */
351 if (!i && (dowarn || strEQ(mg->mg_ptr,"ALARM")))
352 warn("No such signal: SIG%s", mg->mg_ptr);
353 if (strEQ(s,"IGNORE"))
354#ifndef lint
355 (void)signal(i,SIG_IGN);
356#else
357 ;
358#endif
359 else if (strEQ(s,"DEFAULT") || !*s)
360 (void)signal(i,SIG_DFL);
361 else {
362 (void)signal(i,sighandler);
363 if (!index(s,'\'')) {
364 sprintf(tokenbuf, "main'%s",s);
365 sv_setpv(sv,tokenbuf);
366 }
367 }
368 return 0;
369}
370
371int
372magic_setdbm(sv,mg)
373SV* sv;
374MAGIC* mg;
375{
376 HV* hv = (HV*)mg->mg_obj;
377 hv_dbmstore(hv,mg->mg_ptr,mg->mg_len,sv); /* XXX slurp? */
378 return 0;
379}
380
381int
382magic_setdbline(sv,mg)
383SV* sv;
384MAGIC* mg;
385{
386 OP *o;
387 I32 i;
388 GV* gv;
389 SV** svp;
390
391 gv = DBline;
392 i = SvTRUE(sv);
393 svp = av_fetch(GvAV(gv),atoi(mg->mg_ptr), FALSE);
394 if (svp && SvMAGICAL(*svp) && (o = (OP*)SvMAGIC(*svp)->mg_ptr)) {
395#ifdef NOTDEF
396 cmd->cop_flags &= ~COPf_OPTIMIZE;
397 cmd->cop_flags |= i? COPo_D1 : COPo_D0;
398#endif
399 }
400 else
401 warn("Can't break at that line\n");
402 return 0;
403}
404
405int
406magic_getarylen(sv,mg)
407SV* sv;
408MAGIC* mg;
409{
410 sv_setiv(sv, AvFILL((AV*)mg->mg_obj) + arybase);
411 return 0;
412}
413
414int
415magic_setarylen(sv,mg)
416SV* sv;
417MAGIC* mg;
418{
419 av_fill((AV*)mg->mg_obj, (SvIOK(sv) ? SvIV(sv) : sv_2iv(sv)) - arybase);
420 return 0;
421}
422
423int
424magic_getglob(sv,mg)
425SV* sv;
426MAGIC* mg;
427{
428 gv_efullname(sv,((GV*)sv));/* a gv value, be nice */
429 return 0;
430}
431
432int
433magic_setglob(sv,mg)
434SV* sv;
435MAGIC* mg;
436{
437 register char *s;
438 GV* gv;
439
440 if (!SvOK(sv))
441 return 0;
442 s = SvPOK(sv) ? SvPV(sv) : sv_2pv(sv);
443 if (*s == '*' && s[1])
444 s++;
445 gv = gv_fetchpv(s,TRUE);
446 if (sv == (SV*)gv)
447 return 0;
448 if (GvGP(sv))
449 gp_free(sv);
450 GvGP(sv) = gp_ref(GvGP(gv));
451 if (!GvAV(gv))
452 gv_AVadd(gv);
453 if (!GvHV(gv))
454 gv_HVadd(gv);
455 if (!GvIO(gv))
456 GvIO(gv) = newIO();
457 return 0;
458}
459
460int
461magic_setsubstr(sv,mg)
462SV* sv;
463MAGIC* mg;
464{
465 char *tmps = SvPV(sv);
466 if (!tmps)
467 tmps = "";
468 sv_insert(LvTARG(sv),LvTARGOFF(sv),LvTARGLEN(sv), tmps,SvCUR(sv));
469 return 0;
470}
471
472int
473magic_setvec(sv,mg)
474SV* sv;
475MAGIC* mg;
476{
477 do_vecset(sv); /* XXX slurp this routine */
478 return 0;
479}
480
481int
482magic_setbm(sv,mg)
483SV* sv;
484MAGIC* mg;
485{
486 mg_free(sv, 'B');
487 SvVALID_off(sv);
488 return 0;
489}
490
491int
492magic_setuvar(sv,mg)
493SV* sv;
494MAGIC* mg;
495{
496 struct ufuncs *uf = (struct ufuncs *)mg->mg_ptr;
497
498 if (uf && uf->uf_set)
499 (*uf->uf_set)(uf->uf_index, sv);
500 return 0;
501}
502
503int
504magic_set(sv,mg)
505SV* sv;
506MAGIC* mg;
507{
508 register char *s;
509 I32 i;
510 switch (*mg->mg_ptr) {
511 case '\004': /* ^D */
512 debug = (SvIOK(sv) ? SvIV(sv) : sv_2iv(sv)) | 32768;
513 DEBUG_x(dump_all());
514 break;
515 case '\006': /* ^F */
516 maxsysfd = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv);
517 break;
518 case '\t': /* ^I */
519 if (inplace)
520 Safefree(inplace);
521 if (SvOK(sv))
522 inplace = savestr(SvPV(sv));
523 else
524 inplace = Nullch;
525 break;
526 case '\020': /* ^P */
527 i = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv);
528 if (i != perldb) {
529 if (perldb)
530 oldlastpm = curpm;
531 else
532 curpm = oldlastpm;
533 }
534 perldb = i;
535 break;
536 case '\024': /* ^T */
537 basetime = (time_t)(SvIOK(sv) ? SvIV(sv) : sv_2iv(sv));
538 break;
539 case '\027': /* ^W */
540 dowarn = (bool)(SvIOK(sv) ? SvIV(sv) : sv_2iv(sv));
541 break;
542 case '.':
543 if (localizing)
544 save_sptr((SV**)&last_in_gv);
545 break;
546 case '^':
547 Safefree(GvIO(defoutgv)->top_name);
548 GvIO(defoutgv)->top_name = s = savestr(SvPV(sv));
549 GvIO(defoutgv)->top_gv = gv_fetchpv(s,TRUE);
550 break;
551 case '~':
552 Safefree(GvIO(defoutgv)->fmt_name);
553 GvIO(defoutgv)->fmt_name = s = savestr(SvPV(sv));
554 GvIO(defoutgv)->fmt_gv = gv_fetchpv(s,TRUE);
555 break;
556 case '=':
557 GvIO(defoutgv)->page_len = (long)(SvIOK(sv) ? SvIV(sv) : sv_2iv(sv));
558 break;
559 case '-':
560 GvIO(defoutgv)->lines_left = (long)(SvIOK(sv) ? SvIV(sv) : sv_2iv(sv));
561 if (GvIO(defoutgv)->lines_left < 0L)
562 GvIO(defoutgv)->lines_left = 0L;
563 break;
564 case '%':
565 GvIO(defoutgv)->page = (long)(SvIOK(sv) ? SvIV(sv) : sv_2iv(sv));
566 break;
567 case '|':
568 if (!GvIO(defoutgv))
569 GvIO(defoutgv) = newIO();
570 GvIO(defoutgv)->flags &= ~IOf_FLUSH;
571 if ((SvIOK(sv) ? SvIV(sv) : sv_2iv(sv)) != 0) {
572 GvIO(defoutgv)->flags |= IOf_FLUSH;
573 }
574 break;
575 case '*':
576 i = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv);
577 multiline = (i != 0);
578 break;
579 case '/':
580 if (SvPOK(sv)) {
581 rs = SvPV(sv);
582 rslen = SvCUR(sv);
583 if (rspara = !rslen) {
584 rs = "\n\n";
585 rslen = 2;
586 }
587 rschar = rs[rslen - 1];
588 }
589 else {
590 rschar = 0777; /* fake a non-existent char */
591 rslen = 1;
592 }
593 break;
594 case '\\':
595 if (ors)
596 Safefree(ors);
597 ors = savestr(SvPV(sv));
598 orslen = SvCUR(sv);
599 break;
600 case ',':
601 if (ofs)
602 Safefree(ofs);
603 ofs = savestr(SvPV(sv));
604 ofslen = SvCUR(sv);
605 break;
606 case '#':
607 if (ofmt)
608 Safefree(ofmt);
609 ofmt = savestr(SvPV(sv));
610 break;
611 case '[':
612 arybase = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv);
613 break;
614 case '?':
615 statusvalue = U_S(SvIOK(sv) ? SvIV(sv) : sv_2iv(sv));
616 break;
617 case '!':
618 errno = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv); /* will anyone ever use this? */
619 break;
620 case '<':
621 uid = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv);
622 if (delaymagic) {
623 delaymagic |= DM_RUID;
624 break; /* don't do magic till later */
625 }
626#ifdef HAS_SETRUID
627 (void)setruid((UIDTYPE)uid);
628#else
629#ifdef HAS_SETREUID
630 (void)setreuid((UIDTYPE)uid, (UIDTYPE)-1);
631#else
632 if (uid == euid) /* special case $< = $> */
633 (void)setuid(uid);
634 else
635 fatal("setruid() not implemented");
636#endif
637#endif
638 uid = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv);
639 break;
640 case '>':
641 euid = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv);
642 if (delaymagic) {
643 delaymagic |= DM_EUID;
644 break; /* don't do magic till later */
645 }
646#ifdef HAS_SETEUID
647 (void)seteuid((UIDTYPE)euid);
648#else
649#ifdef HAS_SETREUID
650 (void)setreuid((UIDTYPE)-1, (UIDTYPE)euid);
651#else
652 if (euid == uid) /* special case $> = $< */
653 setuid(euid);
654 else
655 fatal("seteuid() not implemented");
656#endif
657#endif
658 euid = (I32)geteuid();
659 break;
660 case '(':
661 gid = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv);
662 if (delaymagic) {
663 delaymagic |= DM_RGID;
664 break; /* don't do magic till later */
665 }
666#ifdef HAS_SETRGID
667 (void)setrgid((GIDTYPE)gid);
668#else
669#ifdef HAS_SETREGID
670 (void)setregid((GIDTYPE)gid, (GIDTYPE)-1);
671#else
672 if (gid == egid) /* special case $( = $) */
673 (void)setgid(gid);
674 else
675 fatal("setrgid() not implemented");
676#endif
677#endif
678 gid = (I32)getgid();
679 break;
680 case ')':
681 egid = SvIOK(sv) ? SvIV(sv) : sv_2iv(sv);
682 if (delaymagic) {
683 delaymagic |= DM_EGID;
684 break; /* don't do magic till later */
685 }
686#ifdef HAS_SETEGID
687 (void)setegid((GIDTYPE)egid);
688#else
689#ifdef HAS_SETREGID
690 (void)setregid((GIDTYPE)-1, (GIDTYPE)egid);
691#else
692 if (egid == gid) /* special case $) = $( */
693 (void)setgid(egid);
694 else
695 fatal("setegid() not implemented");
696#endif
697#endif
698 egid = (I32)getegid();
699 break;
700 case ':':
701 chopset = SvPV(sv);
702 break;
703 case '0':
704 if (!origalen) {
705 s = origargv[0];
706 s += strlen(s);
707 /* See if all the arguments are contiguous in memory */
708 for (i = 1; i < origargc; i++) {
709 if (origargv[i] == s + 1)
710 s += strlen(++s); /* this one is ok too */
711 }
712 if (origenviron[0] == s + 1) { /* can grab env area too? */
713 my_setenv("NoNeSuCh", Nullch);
714 /* force copy of environment */
715 for (i = 0; origenviron[i]; i++)
716 if (origenviron[i] == s + 1)
717 s += strlen(++s);
718 }
719 origalen = s - origargv[0];
720 }
721 s = SvPV(sv);
722 i = SvCUR(sv);
723 if (i >= origalen) {
724 i = origalen;
725 SvCUR_set(sv, i);
726 *SvEND(sv) = '\0';
727 Copy(s, origargv[0], i, char);
728 }
729 else {
730 Copy(s, origargv[0], i, char);
731 s = origargv[0]+i;
732 *s++ = '\0';
733 while (++i < origalen)
734 *s++ = ' ';
735 }
736 break;
737 }
738 return 0;
739}
740
741I32
742whichsig(sig)
743char *sig;
744{
745 register char **sigv;
746
747 for (sigv = sig_name+1; *sigv; sigv++)
748 if (strEQ(sig,*sigv))
749 return sigv - sig_name;
750#ifdef SIGCLD
751 if (strEQ(sig,"CHLD"))
752 return SIGCLD;
753#endif
754#ifdef SIGCHLD
755 if (strEQ(sig,"CLD"))
756 return SIGCHLD;
757#endif
758 return 0;
759}
760
761static handlertype
762sighandler(sig)
763I32 sig;
764{
765 dSP;
766 GV *gv;
767 SV *sv;
768 CV *cv;
769 CONTEXT *cx;
770 AV *oldstack;
771 I32 hasargs = 1;
772 I32 items = 1;
773 I32 gimme = G_SCALAR;
774
775#ifdef OS2 /* or anybody else who requires SIG_ACK */
776 signal(sig, SIG_ACK);
777#endif
778
779 gv = gv_fetchpv(
780 SvPVnx(*hv_fetch(GvHVn(siggv),sig_name[sig],strlen(sig_name[sig]),
781 TRUE)), TRUE);
782 cv = GvCV(gv);
783 if (!cv && *sig_name[sig] == 'C' && instr(sig_name[sig],"LD")) {
784 if (sig_name[sig][1] == 'H')
785 gv = gv_fetchpv(SvPVnx(*hv_fetch(GvHVn(siggv),"CLD",3,TRUE)),
786 TRUE);
787 else
788 gv = gv_fetchpv(SvPVnx(*hv_fetch(GvHVn(siggv),"CHLD",4,TRUE)),
789 TRUE);
790 cv = GvCV(gv); /* gag */
791 }
792 if (!cv) {
793 if (dowarn)
794 warn("SIG%s handler \"%s\" not defined.\n",
795 sig_name[sig], GvENAME(gv) );
796 return;
797 }
798
799 oldstack = stack;
800 SWITCHSTACK(stack, signalstack);
801
802 sv = sv_mortalcopy(&sv_undef);
803 sv_setpv(sv,sig_name[sig]);
804 PUSHs(sv);
805
806 ENTER;
807 SAVETMPS;
808
809 push_return(op);
810 push_return(0);
811 PUSHBLOCK(cx, CXt_SUB, sp);
812 PUSHSUB(cx);
813 cx->blk_sub.savearray = GvAV(defgv);
814 cx->blk_sub.argarray = av_fake(items, sp);
815 GvAV(defgv) = cx->blk_sub.argarray;
816 CvDEPTH(cv)++;
817 if (CvDEPTH(cv) >= 2) {
818 if (CvDEPTH(cv) == 100 && dowarn)
819 warn("Deep recursion on subroutine \"%s\"",GvENAME(gv));
820 }
821 op = CvSTART(cv);
822 PUTBACK;
823 run(); /* Does the LEAVE for us. */
824
825 SWITCHSTACK(signalstack, oldstack);
826 op = pop_return();
827
828 return;
829}
830
831#ifdef OLD
832 if (sv->sv_magic && !sv->sv_rare) {
833 GV *gv = sv->sv_magic->sv_u.sv_gv;
834
835 switch (*SvPV(gv->sv_magic)) {
836 case '1': case '2': case '3': case '4':
837 case '5': case '6': case '7': case '8': case '9': case '&':
838 if (curpm) {
839 paren = atoi(GvENAME(gv));
840 getparen:
841 if (curpm->op_pmregexp &&
842 paren <= curpm->op_pmregexp->nparens &&
843 (s = curpm->op_pmregexp->startp[paren]) ) {
844 i = curpm->op_pmregexp->endp[paren] - s;
845 if (i >= 0)
846 return i;
847 else
848 return 0;
849 }
850 else
851 return 0;
852 }
853 break;
854 case '+':
855 if (curpm) {
856 paren = curpm->op_pmregexp->lastparen;
857 goto getparen;
858 }
859 break;
860 case '`':
861 if (curpm) {
862 if (curpm->op_pmregexp &&
863 (s = curpm->op_pmregexp->subbeg) ) {
864 i = curpm->op_pmregexp->startp[0] - s;
865 if (i >= 0)
866 return i;
867 else
868 return 0;
869 }
870 else
871 return 0;
872 }
873 break;
874 case '\'':
875 if (curpm) {
876 if (curpm->op_pmregexp &&
877 (s = curpm->op_pmregexp->endp[0]) ) {
878 return (STRLEN) (curpm->op_pmregexp->subend - s);
879 }
880 else
881 return 0;
882 }
883 break;
884 case ',':
885 return (STRLEN)ofslen;
886 case '\\':
887 return (STRLEN)orslen;
888 }
889 sv = gv_str(sv);
890 }
891#endif