[dovecot-cvs] dovecot/src/lib ioloop-internal.h, 1.11, 1.12 ioloop-poll.c, 1.22, 1.23 ioloop-select.c, 1.18, 1.19 ioloop.c, 1.24, 1.25

cras at dovecot.org cras at dovecot.org
Wed Aug 25 15:27:46 EEST 2004


Update of /home/cvs/dovecot/src/lib
In directory talvi:/tmp/cvs-serv18994/lib

Modified Files:
	ioloop-internal.h ioloop-poll.c ioloop-select.c ioloop.c 
Log Message:
Changed io_remove() to destroy the io immediately. Changed struct io to be
double linked list. Moved highest_fd into select-specific struct. Some minor
optimizations.



Index: ioloop-internal.h
===================================================================
RCS file: /home/cvs/dovecot/src/lib/ioloop-internal.h,v
retrieving revision 1.11
retrieving revision 1.12
diff -u -d -r1.11 -r1.12
--- ioloop-internal.h	23 Aug 2004 13:47:32 -0000	1.11
+++ ioloop-internal.h	25 Aug 2004 12:27:44 -0000	1.12
@@ -7,10 +7,10 @@
         struct ioloop *prev;
 
 	pool_t pool;
-	int highest_fd;
 
 	struct io *ios;
 	struct io *notifys, *event_io;
+	struct io *next_io;
 	struct timeout *timeouts; /* sorted by next_run */
 
         struct ioloop_handler_data *handler_data;
@@ -19,13 +19,11 @@
 };
 
 struct io {
-	struct io *next;
+	struct io *prev, *next;
 
 	int fd;
 	enum io_condition condition;
 
-	unsigned int destroyed:1;
-
 	io_callback_t *callback;
         void *context;
 };
@@ -47,8 +45,6 @@
 			  struct timeval *tv_now);
 void io_loop_handle_timeouts(struct ioloop *ioloop);
 
-/* call only when io->destroyed is TRUE */
-void io_destroy(struct ioloop *ioloop, struct io **io_p);
 /* call only when timeout->destroyed is TRUE */
 void timeout_destroy(struct ioloop *ioloop, struct timeout **timeout_p);
 

Index: ioloop-poll.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib/ioloop-poll.c,v
retrieving revision 1.22
retrieving revision 1.23
diff -u -d -r1.22 -r1.23
--- ioloop-poll.c	23 Aug 2004 13:47:32 -0000	1.22
+++ ioloop-poll.c	25 Aug 2004 12:27:44 -0000	1.23
@@ -132,7 +132,7 @@
 	struct ioloop_handler_data *data = ioloop->handler_data;
         struct pollfd *pollfd;
         struct timeval tv;
-	struct io *io, **io_p;
+	struct io *io;
 	unsigned int t_id;
 	int msecs, ret, call;
 
@@ -151,17 +151,8 @@
 		return;
 	}
 
-	io_p = &ioloop->ios;
-	for (io = ioloop->ios; io != NULL && ret > 0; io = *io_p) {
-		if (io->destroyed) {
-			/* we were destroyed, and io->fd points to
-			   -1 now, so we can't know if there was any
-			   revents left. */
-			io_destroy(ioloop, io_p);
-			continue;
-		}
-
-		i_assert(io->fd >= 0);
+	for (io = ioloop->ios; io != NULL && ret > 0; io = ioloop->next_io) {
+		ioloop->next_io = io->next;
 
 		pollfd = &data->fds[data->fd_index[io->fd]];
 		if (pollfd->revents != 0) {
@@ -193,15 +184,8 @@
 				io->callback(io->context);
 				if (t_pop() != t_id)
 					i_panic("Leaked a t_pop() call!");
-
-				if (io->destroyed) {
-					io_destroy(ioloop, io_p);
-					continue;
-				}
 			}
 		}
-
-		io_p = &io->next;
 	}
 }
 

Index: ioloop-select.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib/ioloop-select.c,v
retrieving revision 1.18
retrieving revision 1.19
diff -u -d -r1.18 -r1.19
--- ioloop-select.c	25 Aug 2004 12:09:09 -0000	1.18
+++ ioloop-select.c	25 Aug 2004 12:27:44 -0000	1.19
@@ -12,6 +12,7 @@
 #include <unistd.h>
 
 struct ioloop_handler_data {
+	int highest_fd;
 	fd_set read_fds, write_fds;
 };
 
@@ -22,14 +23,14 @@
         struct io *io;
 	int max_highest_fd;
 
-        max_highest_fd = ioloop->highest_fd-1;
-	ioloop->highest_fd = -1;
+        max_highest_fd = ioloop->handler_data->highest_fd-1;
+	ioloop->handler_data->highest_fd = -1;
 
 	for (io = ioloop->ios; io != NULL; io = io->next) {
-		if (!io->destroyed && io->fd > ioloop->highest_fd) {
-			ioloop->highest_fd = io->fd;
+		if (io->fd > ioloop->handler_data->highest_fd) {
+			ioloop->handler_data->highest_fd = io->fd;
 
-			if (ioloop->highest_fd == max_highest_fd)
+			if (ioloop->handler_data->highest_fd == max_highest_fd)
                                 break;
 		}
 	}
@@ -37,9 +38,9 @@
 
 void io_loop_handler_init(struct ioloop *ioloop)
 {
-	ioloop->highest_fd = -1;
 	ioloop->handler_data =
 		p_new(ioloop->pool, struct ioloop_handler_data, 1);
+	ioloop->handler_data->highest_fd = -1;
         FD_ZERO(&ioloop->handler_data->read_fds);
 	FD_ZERO(&ioloop->handler_data->write_fds);
 }
@@ -64,8 +65,8 @@
         if (condition & IO_WRITE)
 		FD_SET(fd, &ioloop->handler_data->write_fds);
 
-	if (io->fd > ioloop->highest_fd)
-		ioloop->highest_fd = io->fd;
+	if (io->fd > ioloop->handler_data->highest_fd)
+		ioloop->handler_data->highest_fd = io->fd;
 }
 
 void io_loop_handle_remove(struct ioloop *ioloop, struct io *io)
@@ -81,18 +82,18 @@
 		FD_CLR(fd, &ioloop->handler_data->write_fds);
 
 	/* check if we removed the highest fd */
-	if (io->fd == ioloop->highest_fd)
+	if (io->fd == ioloop->handler_data->highest_fd)
 		update_highest_fd(ioloop);
 }
 
 #define io_check_condition(fd, condition) \
-	((((condition) & IO_READ) && FD_ISSET((fd), &tmp_read_fds)) || \
-	 (((condition) & IO_WRITE) && FD_ISSET((fd), &tmp_write_fds)))
+	((FD_ISSET((fd), &tmp_read_fds) && ((condition) & IO_READ)) || \
+	 (FD_ISSET((fd), &tmp_write_fds) && ((condition) & IO_WRITE)))
 
 void io_loop_handler_run(struct ioloop *ioloop)
 {
 	struct timeval tv;
-	struct io *io, **io_p;
+	struct io *io;
 	unsigned int t_id;
 	int ret;
 
@@ -103,8 +104,8 @@
 	memcpy(&tmp_write_fds, &ioloop->handler_data->write_fds,
 	       sizeof(fd_set));
 
-	ret = select(ioloop->highest_fd + 1, &tmp_read_fds, &tmp_write_fds,
-		     NULL, &tv);
+	ret = select(ioloop->handler_data->highest_fd + 1,
+		     &tmp_read_fds, &tmp_write_fds, NULL, &tv);
 	if (ret < 0 && errno != EINTR)
 		i_warning("select() : %m");
 
@@ -116,15 +117,8 @@
 		return;
 	}
 
-	io_p = &ioloop->ios;
-	for (io = ioloop->ios; io != NULL && ret > 0; io = *io_p) {
-		if (io->destroyed) {
-			/* we were destroyed, and io->fd points to -1 now. */
-			io_destroy(ioloop, io_p);
-			continue;
-		}
-
-		i_assert(io->fd >= 0);
+	for (io = ioloop->ios; io != NULL && ret > 0; io = ioloop->next_io) {
+                ioloop->next_io = io->next;
 
 		if (io_check_condition(io->fd, io->condition)) {
 			ret--;
@@ -133,14 +127,7 @@
 			io->callback(io->context);
 			if (t_pop() != t_id)
 				i_panic("Leaked a t_pop() call!");
-
-			if (io->destroyed) {
-				io_destroy(ioloop, io_p);
-				continue;
-			}
 		}
-
-		io_p = &io->next;
 	}
 }
 

Index: ioloop.c
===================================================================
RCS file: /home/cvs/dovecot/src/lib/ioloop.c,v
retrieving revision 1.24
retrieving revision 1.25
diff -u -d -r1.24 -r1.25
--- ioloop.c	25 Aug 2004 12:09:09 -0000	1.24
+++ ioloop.c	25 Aug 2004 12:27:44 -0000	1.25
@@ -18,7 +18,7 @@
 struct io *io_add(int fd, enum io_condition condition,
 		  io_callback_t *callback, void *context)
 {
-	struct io *io, **io_p;
+	struct io *io;
 
 	i_assert(fd >= 0);
 	i_assert(callback != NULL);
@@ -38,18 +38,16 @@
 	io_loop_handle_add(current_ioloop, io);
 
 	/* have to append it, or io_destroy() breaks */
-        io_p = &current_ioloop->ios;
-	while (*io_p != NULL)
-		io_p = &(*io_p)->next;
-	*io_p = io;
+	io->next = current_ioloop->ios;
+	current_ioloop->ios = io;
+
+	if (io->next != NULL)
+		io->next->prev = io;
 	return io;
 }
 
 void io_remove(struct io *io)
 {
-	i_assert(io != NULL);
-	i_assert(io->fd >= 0);
-
 	if ((io->condition & IO_NOTIFY_MASK) != 0) {
 		io_loop_notify_remove(current_ioloop, io);
 		return;
@@ -58,18 +56,17 @@
 	/* notify the real I/O handler */
 	io_loop_handle_remove(current_ioloop, io);
 
-	io->destroyed = TRUE;
-
-	io->fd = -1;
-}
+	if (current_ioloop->next_io == io)
+                current_ioloop->next_io = io->next;
 
-void io_destroy(struct ioloop *ioloop, struct io **io_p)
-{
-	struct io *io = *io_p;
+	if (io->prev == NULL)
+		current_ioloop->ios = io->next;
+	else
+		io->prev->next = io->next;
+	if (io->next != NULL)
+		io->next->prev = io->prev;
 
-	/* remove from list */
-	*io_p = io->next;
-	p_free(ioloop->pool, io);
+	p_free(current_ioloop->pool, io);
 }
 
 static void timeout_list_insert(struct ioloop *ioloop, struct timeout *timeout)
@@ -264,19 +261,15 @@
 	while (ioloop->ios != NULL) {
 		struct io *io = ioloop->ios;
 
-		if (!io->destroyed) {
-			i_warning("I/O leak: %p (%d)",
-				  (void *) io->callback, io->fd);
-			io_remove(io);
-		}
-		io_destroy(ioloop, &ioloop->ios);
+		i_warning("I/O leak: %p (%d)", (void *)io->callback, io->fd);
+		io_remove(io);
 	}
 
 	while (ioloop->timeouts != NULL) {
 		struct timeout *to = ioloop->timeouts;
 
 		if (!to->destroyed) {
-			i_warning("Timeout leak: %p", (void *) to->callback);
+			i_warning("Timeout leak: %p", (void *)to->callback);
 			timeout_remove(to);
 		}
                 timeout_destroy(ioloop, &ioloop->timeouts);



More information about the dovecot-cvs mailing list