changeset 18039:1632ae08c986

lib: io_remove() should finish closing the io before unreferencing its istream. This is because the istream unreferencing may close the fd.
author Timo Sirainen <tss@iki.fi>
date Tue, 28 Oct 2014 17:07:21 -0700
parents d92214db89ac
children 0393f550fd82
files src/lib/ioloop.c
diffstat 1 files changed, 9 insertions(+), 6 deletions(-) [+]
line wrap: on
line diff
--- a/src/lib/ioloop.c	Tue Oct 28 16:12:09 2014 -0700
+++ b/src/lib/ioloop.c	Tue Oct 28 17:07:21 2014 -0700
@@ -136,16 +136,19 @@
 		io_loop_notify_remove(io);
 	else {
 		struct io_file *io_file = (struct io_file *)io;
-
-		if (io_file->istream != NULL) {
-			i_stream_unset_io(io_file->istream, io);
-			i_stream_unref(&io_file->istream);
-			io_file->istream = NULL;
-		}
+		struct istream *istream = io_file->istream;
 
 		io_file_unlink(io_file);
 		if (io_file->fd != -1)
 			io_loop_handle_remove(io_file, closed);
+
+		/* remove io from the ioloop before unreferencing the istream,
+		   because a destroyed istream may automatically close the
+		   fd. */
+		if (istream != NULL) {
+			i_stream_unset_io(istream, io);
+			i_stream_unref(&istream);
+		}
 	}
 }