summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDave Mitchell <davem@fdisolutions.com>2007-01-03 22:17:48 +0000
committerDave Mitchell <davem@fdisolutions.com>2007-01-03 22:17:48 +0000
commit7c197c94dc644853d0512a443fd0e99a5f287ad0 (patch)
tree1ba6b14de8f6cd9ad2c4814d1c35f491e4b74cad
parent0e4c4423f4f1412e4eeb73b8af7f846ea7b0c4bc (diff)
downloadperl-7c197c94dc644853d0512a443fd0e99a5f287ad0.tar.gz
handle cloning of parsers on the save stack
p4raw-id: //depot/perl@29678
-rw-r--r--perly.c2
-rw-r--r--scope.c4
-rw-r--r--scope.h8
-rw-r--r--sv.c11
4 files changed, 24 insertions, 1 deletions
diff --git a/perly.c b/perly.c
index 4e3a7e2218..8ce76abf7a 100644
--- a/perly.c
+++ b/perly.c
@@ -348,7 +348,7 @@ Perl_yyparse (pTHX)
ps = parser->ps;
ENTER; /* force parser free before we return */
- SAVEDESTRUCTOR_X(Perl_parser_free, (void*) parser);
+ SAVEPARSER(parser);
/*------------------------------------------------------------.
| yynewstate -- Push a new state, which is found in yystate. |
diff --git a/scope.c b/scope.c
index abe9a0542b..d15d2d93c1 100644
--- a/scope.c
+++ b/scope.c
@@ -1023,6 +1023,10 @@ Perl_leave_scope(pTHX_ I32 base)
Copy(state, &PL_reg_state, 1, struct re_save_state);
}
break;
+ case SAVEt_PARSER:
+ ptr = SSPOPPTR;
+ parser_free((yy_parser *) ptr);
+ break;
default:
Perl_croak(aTHX_ "panic: leave_scope inconsistency");
}
diff --git a/scope.h b/scope.h
index c80430066f..40e9fe6f3d 100644
--- a/scope.h
+++ b/scope.h
@@ -53,6 +53,7 @@
#define SAVEt_RE_STATE 42
#define SAVEt_COMPILE_WARNINGS 43
#define SAVEt_STACK_CXPOS 44
+#define SAVEt_PARSER 45
#ifndef SCOPE_SAVES_SIGNAL_MASK
#define SCOPE_SAVES_SIGNAL_MASK 0
@@ -214,6 +215,13 @@ Closing bracket on a callback. See C<ENTER> and L<perlcall>.
SSPUSHINT(SAVEt_STACK_CXPOS); \
} STMT_END
+#define SAVEPARSER(p) \
+ STMT_START { \
+ SSCHECK(2); \
+ SSPUSHPTR(p); \
+ SSPUSHINT(SAVEt_PARSER); \
+ } STMT_END
+
#ifdef USE_ITHREADS
# define SAVECOPSTASH(c) SAVEPPTR(CopSTASHPV(c))
# define SAVECOPSTASH_FREE(c) SAVESHAREDPV(CopSTASHPV(c))
diff --git a/sv.c b/sv.c
index 8bed94185d..15f54d85ce 100644
--- a/sv.c
+++ b/sv.c
@@ -9498,7 +9498,14 @@ Perl_parser_dup(pTHX_ const yy_parser *proto, CLONE_PARAMS* param)
if (!proto)
return NULL;
+ /* look for it in the table first */
+ parser = (yy_parser *)ptr_table_fetch(PL_ptr_table, proto);
+ if (parser)
+ return parser;
+
+ /* create anew and remember what it is */
Newxz(parser, 1, yy_parser);
+ ptr_table_store(PL_ptr_table, proto, parser);
parser->yyerrstatus = 0;
parser->yychar = YYEMPTY; /* Cause a token to be read. */
@@ -10670,6 +10677,10 @@ Perl_ss_dup(pTHX_ PerlInterpreter *proto_perl, CLONE_PARAMS* param)
ptr = POPPTR(ss,ix);
TOPPTR(nss,ix) = DUP_WARNINGS((STRLEN*)ptr);
break;
+ case SAVEt_PARSER:
+ ptr = POPPTR(ss,ix);
+ TOPPTR(nss,ix) = parser_dup(ptr, param);
+ break;
default:
Perl_croak(aTHX_
"panic: ss_dup inconsistency (%"IVdf")", (IV) type);