changeset 17656:2b1047efc4fb classdef

don't leak memory when parsing classdef objects fails * oct-parse.in.yy (octave_base_parser::make_classdef, octave_base_parser::make_classdef_properties_block, octave_base_parser::make_classdef_methods_block, octave_base_parser::make_classdef_events_block, octave_base_parser::make_classdef_enum_block): Delete component parse tree elements on error.
author John W. Eaton <jwe@octave.org>
date Mon, 14 Oct 2013 16:49:14 -0400
parents d7da5afcdb22
children df266c923b83
files libinterp/parse-tree/oct-parse.in.yy
diffstat 1 files changed, 56 insertions(+), 17 deletions(-) [+]
line wrap: on
line diff
--- a/libinterp/parse-tree/oct-parse.in.yy	Mon Oct 14 16:15:13 2013 -0400
+++ b/libinterp/parse-tree/oct-parse.in.yy	Mon Oct 14 16:49:14 2013 -0400
@@ -1446,7 +1446,10 @@
                     lexer.parsing_classdef = false;
 
                     if (! ($$ = parser.make_classdef ($1, $3, $4, $5, $7, $9, $2)))
-                      ABORT_PARSE;
+                      {
+                        // make_classdef deleted $3, $4, $5, and $7.
+                        ABORT_PARSE;
+                      }
                   }
                 ;
 
@@ -1532,8 +1535,11 @@
                 : PROPERTIES stash_comment opt_attr_list opt_sep property_list opt_sep END
                   {
                     if (! ($$ = parser.make_classdef_properties_block
-                                              ($1, $3, $5, $7, $2)))
-                      ABORT_PARSE;
+                           ($1, $3, $5, $7, $2)))
+                      {
+                        // make_classdef_properties_block delete $3 and $5.
+                        ABORT_PARSE;
+                      }
                   }
                 ;
 
@@ -1559,8 +1565,11 @@
 methods_block   : METHODS stash_comment opt_attr_list opt_sep methods_list opt_sep END
                   {
                     if (! ($$ = parser.make_classdef_methods_block
-                                              ($1, $3, $5, $7, $2)))
-                      ABORT_PARSE;
+                           ($1, $3, $5, $7, $2)))
+                      {
+                        // make_classdef_methods_block deleted $3 and $5.
+                        ABORT_PARSE;
+                      }
                   }
                 ;
 
@@ -1587,8 +1596,11 @@
 events_block    : EVENTS stash_comment opt_attr_list opt_sep events_list opt_sep END
                   {
                     if (! ($$ = parser.make_classdef_events_block
-                                              ($1, $3, $5, $7, $2)))
-                      ABORT_PARSE;
+                           ($1, $3, $5, $7, $2)))
+                      {
+                        // make_classdef_events_block deleted $3 and $5.
+                        ABORT_PARSE;
+                      }
                   }
                 ;
 
@@ -1608,8 +1620,11 @@
 enum_block      : ENUMERATION stash_comment opt_attr_list opt_sep enum_list opt_sep END
                   {
                     if (! ($$ = parser.make_classdef_enum_block
-                                              ($1, $3, $5, $7, $2)))
-                      ABORT_PARSE;
+                           ($1, $3, $5, $7, $2)))
+                      {
+                        // make_classdef_enum_block deleted $3 and $5.
+                        ABORT_PARSE;
+                      }
                   }
                 ;
 
@@ -3132,20 +3147,24 @@
     nm = lexer.fcn_file_name.substr (pos+1);
 
   if (nm != cls_name)
-    {
-      bison_error ("invalid classdef definition, the class name must match the file name");
-      return retval;
-    }
-
-  if (end_token_ok (end_tok, token::classdef_end))
+    bison_error ("invalid classdef definition, the class name must match the file name");
+  else if (end_token_ok (end_tok, token::classdef_end))
     {
       octave_comment_list *tc = octave_comment_buffer::get_comment ();
 
       int l = tok_val->line ();
       int c = tok_val->column ();
 
-      retval = new tree_classdef (a, id, sc, body, lc, tc, curr_package_name,
-                                  l, c);
+      retval = new tree_classdef (a, id, sc, body, lc, tc,
+                                  curr_package_name, l, c);
+    }
+
+  if (! retval)
+    {
+      delete a;
+      delete id;
+      delete sc;
+      delete body;
     }
 
   return retval;
@@ -3169,6 +3188,11 @@
 
       retval = new tree_classdef_properties_block (a, plist, lc, tc, l, c);
     }
+  else
+    {
+      delete a;
+      delete plist;
+    }
 
   return retval;
 }
@@ -3191,6 +3215,11 @@
 
       retval = new tree_classdef_methods_block (a, mlist, lc, tc, l, c);
     }
+  else
+    {
+      delete a;
+      delete mlist;
+    }
 
   return retval;
 }
@@ -3213,6 +3242,11 @@
 
       retval = new tree_classdef_events_block (a, elist, lc, tc, l, c);
     }
+  else
+    {
+      delete a;
+      delete elist;
+    }
 
   return retval;
 }
@@ -3235,6 +3269,11 @@
 
       retval = new tree_classdef_enum_block (a, elist, lc, tc, l, c);
     }
+  else
+    {
+      delete a;
+      delete elist;
+    }
 
   return retval;
 }