Plugs a memory leak on destruction of regular expressions
Artur Bergman [Mon, 27 Aug 2001 05:37:17 +0000 (05:37 +0000)]
introcued by #11274.
PL_regex_padav now has an AV as it's first entry with a list
of freed regex_padav slots that it will reuse on creating
new PMOPs.

p4raw-id: //depot/perl@11755

op.c
perl.c

diff --git a/op.c b/op.c
index 677fe7a..030fabe 100644 (file)
--- a/op.c
+++ b/op.c
@@ -747,6 +747,7 @@ Perl_op_free(pTHX_ OP *o)
 void
 Perl_op_clear(pTHX_ OP *o)
 {
+
     switch (o->op_type) {
     case OP_NULL:      /* Was holding old type, if any. */
     case OP_ENTEREVAL: /* Was holding hints. */
@@ -860,6 +861,13 @@ clear_pmop:
          */
        ReREFCNT_dec(PM_GETRE_SAFE(cPMOPo));
        PM_SETRE_SAFE(cPMOPo, (REGEXP*)NULL);
+#ifdef USE_ITHREADS
+       if(PL_regex_pad) {        /* We could be in destruction */
+            av_push((AV*) PL_regex_pad[0],(SV*) PL_regex_pad[(cPMOPo)->op_pmoffset]);
+            PM_SETRE(cPMOPo, (cPMOPo)->op_pmoffset);
+        }
+#endif 
+
        break;
     }
 
@@ -2962,12 +2970,19 @@ Perl_newPMOP(pTHX_ I32 type, I32 flags)
     pmop->op_pmflags = pmop->op_pmpermflags;
 
 #ifdef USE_ITHREADS
-        {
-                SV* repointer = newSViv(0);
-                av_push(PL_regex_padav,SvREFCNT_inc(repointer));
-                pmop->op_pmoffset = av_len(PL_regex_padav);
-                PL_regex_pad = AvARRAY(PL_regex_padav);
+    {
+        SV* repointer;
+        if(av_len((AV*) PL_regex_pad[0]) > -1) {
+           repointer = av_pop((AV*)PL_regex_pad[0]);
+            pmop->op_pmoffset = SvIV(repointer);
+           sv_setiv(repointer,0);
+        } else { 
+            repointer = newSViv(0);
+            av_push(PL_regex_padav,SvREFCNT_inc(repointer));
+            pmop->op_pmoffset = av_len(PL_regex_padav);
+            PL_regex_pad = AvARRAY(PL_regex_padav);
         }
+    }
 #endif
         
         /* link into pm list */
diff --git a/perl.c b/perl.c
index 4bda944..8ad313e 100644 (file)
--- a/perl.c
+++ b/perl.c
@@ -284,7 +284,9 @@ perl_construct(pTHXx)
     PL_modglobal = newHV();            /* pointers to per-interpreter module globals */
     PL_errors = newSVpvn("",0);
 #ifdef USE_ITHREADS
-        PL_regex_padav = newAV();
+    PL_regex_padav = newAV();
+    av_push(PL_regex_padav,(SV*)newAV());    /* First entry is an array of empty elements */
+    PL_regex_pad = AvARRAY(PL_regex_padav);
 #endif
 #ifdef USE_REENTRANT_API
     New(31337, PL_reentrant_buffer,1, REBUF);