]> git.ipfire.org Git - thirdparty/sqlalchemy/sqlalchemy.git/commitdiff
Fix memory leaks in the cprocessors DecimalResultProcessor, including tests. [ticket...
authorTaavi Burns <taavi.burns@gmail.com>
Fri, 19 Nov 2010 22:44:39 +0000 (17:44 -0500)
committerTaavi Burns <taavi.burns@gmail.com>
Fri, 19 Nov 2010 22:44:39 +0000 (17:44 -0500)
lib/sqlalchemy/cextension/processors.c
test/aaa_profiling/test_memusage.py

index 327462fa89dde110d297e78a5ce529fa48ea93aa..193fb19f30cea75d987bda045552a68e15990fe5 100644 (file)
@@ -289,6 +289,7 @@ DecimalResultProcessor_process(DecimalResultProcessor *self, PyObject *value)
             return NULL;
 
         str = PyString_Format(self->format, args);
+        Py_DECREF(args);
         if (str == NULL)
             return NULL;
 
@@ -300,6 +301,14 @@ DecimalResultProcessor_process(DecimalResultProcessor *self, PyObject *value)
     }
 }
 
+static void
+DecimalResultProcessor_dealloc(DecimalResultProcessor *self)
+{
+    Py_XDECREF(self->type);
+    Py_XDECREF(self->format);
+    self->ob_type->tp_free((PyObject*)self);
+}
+
 static PyMethodDef DecimalResultProcessor_methods[] = {
     {"process", (PyCFunction)DecimalResultProcessor_process, METH_O,
      "The value processor itself."},
@@ -312,7 +321,7 @@ static PyTypeObject DecimalResultProcessorType = {
     "sqlalchemy.DecimalResultProcessor",        /* tp_name */
     sizeof(DecimalResultProcessor),             /* tp_basicsize */
     0,                                          /* tp_itemsize */
-    0,                                          /* tp_dealloc */
+    (destructor)DecimalResultProcessor_dealloc, /* tp_dealloc */
     0,                                          /* tp_print */
     0,                                          /* tp_getattr */
     0,                                          /* tp_setattr */
index 5fa40a99781413d6d50c9aabb34f9f238bde206c..3fb6bfa55adb2291e960973bbb0d9da1dc21c27a 100644 (file)
@@ -7,10 +7,11 @@ from sqlalchemy.util import jython
 import operator
 from sqlalchemy.test import testing, engines
 from sqlalchemy import MetaData, Integer, String, ForeignKey, \
-    PickleType, create_engine, Unicode
+    PickleType, create_engine, Unicode, Float
 from sqlalchemy.test.schema import Table, Column
 import sqlalchemy as sa
 from sqlalchemy.sql import column
+from sqlalchemy.processors import to_decimal_processor_factory
 from sqlalchemy.test.util import gc_collect
 import gc
 import weakref
@@ -566,3 +567,42 @@ class MemUsageTest(EnsureZeroed):
             cast.compile(dialect=dialect)
         go()
         
+    def test_DecimalResultProcessor_processing(self):
+        metadata = MetaData(testing.db)
+
+        table1 = Table("mytable", metadata,
+            Column('col1', Integer, primary_key=True,
+                                    test_needs_autoincrement=True),
+            Column('col2', Float(asdecimal=True))
+            )
+
+        class Foo(object):
+            def __init__(self, col2):
+                self.col2 = col2
+
+        mapper(Foo, table1)
+        metadata.create_all()
+        
+        session = create_session()
+        session.begin()
+        session.add(Foo(1.1))
+        session.commit()
+        session.close()
+        del session
+
+        @profile_memory
+        def go():
+            session = create_session()
+            session.query(Foo).all()
+            session.rollback()
+            session.close()
+        try:
+            go()
+        finally:
+            metadata.drop_all()
+
+    def test_DecimalResultProcessor_dealloc(self):
+        @profile_memory
+        def go():
+            to_decimal_processor_factory({}, 10)
+        go()