]> granicus.if.org Git - python/commitdiff
Issue #9295: Fix a crash under Windows when calling close() on a file
authorAntoine Pitrou <solipsis@pitrou.net>
Thu, 28 Oct 2010 14:50:57 +0000 (14:50 +0000)
committerAntoine Pitrou <solipsis@pitrou.net>
Thu, 28 Oct 2010 14:50:57 +0000 (14:50 +0000)
object with custom buffering from two threads at once.

Misc/NEWS
Objects/fileobject.c

index fa41945c919687599ea532abe33a4fb28d22c8ad..665271ec761a334019ad42d4395a4900ea14475c 100644 (file)
--- a/Misc/NEWS
+++ b/Misc/NEWS
@@ -63,6 +63,9 @@ Core and Builtins
 Library
 -------
 
+- Issue #9295: Fix a crash under Windows when calling close() on a file
+  object with custom buffering from two threads at once.
+
 - Issue #5027: The standard ``xml`` namespace is now understood by
   xml.sax.saxutils.XMLGenerator as being bound to
   http://www.w3.org/XML/1998/namespace.  Patch by Troy J. Farrell.
index 2647b54269ca864a8c6c74e0b07072bcb7db0099..974d6424e4f4b0f61c6efa22715be7e3f94b1184 100644 (file)
@@ -423,6 +423,7 @@ close_the_file(PyFileObject *f)
     int sts = 0;
     int (*local_close)(FILE *);
     FILE *local_fp = f->f_fp;
+    char *local_setbuf = f->f_setbuf;
     if (local_fp != NULL) {
         local_close = f->f_close;
         if (local_close != NULL && f->unlocked_count > 0) {
@@ -446,10 +447,15 @@ close_the_file(PyFileObject *f)
          * called. */
         f->f_fp = NULL;
         if (local_close != NULL) {
+            /* Issue #9295: must temporarily reset f_setbuf so that another
+               thread doesn't free it when running file_close() concurrently.
+               Otherwise this close() will crash when flushing the buffer. */
+            f->f_setbuf = NULL;
             Py_BEGIN_ALLOW_THREADS
             errno = 0;
             sts = (*local_close)(local_fp);
             Py_END_ALLOW_THREADS
+            f->f_setbuf = local_setbuf;
             if (sts == EOF)
                 return PyErr_SetFromErrno(PyExc_IOError);
             if (sts != 0)