dovecot-1.2: Added net_listen_unix_unlink_stale() and use it whe...

dovecot at dovecot.org dovecot at dovecot.org
Sat Sep 27 12:20:31 EEST 2008


details:   http://hg.dovecot.org/dovecot-1.2/rev/ec83f6dcb585
changeset: 8219:ec83f6dcb585
user:      Timo Sirainen <tss at iki.fi>
date:      Sat Sep 27 12:20:26 2008 +0300
description:
Added net_listen_unix_unlink_stale() and use it where needed to avoid code duplication.

diffstat:

6 files changed, 53 insertions(+), 63 deletions(-)
src/auth/main.c              |   25 ++++++++-----------------
src/dict/dict-server.c       |   20 +++++---------------
src/lib/network.c            |   27 +++++++++++++++++++++++++++
src/lib/network.h            |    4 ++++
src/lib/unix-socket-create.c |    4 +---
src/master/dict-process.c    |   36 ++++++++----------------------------

diffs (194 lines):

diff -r 2df7a88a5458 -r ec83f6dcb585 src/auth/main.c
--- a/src/auth/main.c	Wed Sep 24 23:33:59 2008 +0300
+++ b/src/auth/main.c	Sat Sep 27 12:20:26 2008 +0300
@@ -101,7 +101,7 @@ static int create_unix_listener(const ch
 	unsigned int mask;
 	uid_t uid;
 	gid_t gid;
-	int fd, i;
+	int fd;
 
 	path = getenv(env);
 	if (path == NULL)
@@ -117,23 +117,14 @@ static int create_unix_listener(const ch
 	}
 
 	old_umask = umask(mask);
-	for (i = 0; i < 5; i++) {
-		fd = net_listen_unix(path, backlog);
-		if (fd != -1)
-			break;
-
-		if (errno != EADDRINUSE)
+	fd = net_listen_unix_unlink_stale(path, backlog);
+	umask(old_umask);
+	if (fd == -1) {
+		if (errno == EADDRINUSE)
+			i_fatal("Socket already exists: %s", path);
+		else
 			i_fatal("net_listen_unix(%s) failed: %m", path);
-
-		/* see if it really exists */
-		if (net_connect_unix(path) != -1 || errno != ECONNREFUSED)
-			i_fatal("Socket already exists: %s", path);
-
-		/* delete and try again */
-		if (unlink(path) < 0)
-			i_fatal("unlink(%s) failed: %m", path);
-	}
-	umask(old_umask);
+	}
 
 	user = getenv(t_strdup_printf("%s_USER", env));
 	group = getenv(t_strdup_printf("%s_GROUP", env));
diff -r 2df7a88a5458 -r ec83f6dcb585 src/dict/dict-server.c
--- a/src/dict/dict-server.c	Wed Sep 24 23:33:59 2008 +0300
+++ b/src/dict/dict-server.c	Sat Sep 27 12:20:26 2008 +0300
@@ -521,27 +521,17 @@ struct dict_server *dict_server_init(con
 struct dict_server *dict_server_init(const char *path, int fd)
 {
 	struct dict_server *server;
-	int i= 0;
 
 	server = i_new(struct dict_server, 1);
 	server->path = i_strdup(path);
 	server->fd = fd;
 
-	while (server->fd == -1) {
-		server->fd = net_listen_unix(path, 64);
-		if (server->fd != -1)
-			break;
-
-		if (errno != EADDRINUSE || ++i == 2)
+	server->fd = net_listen_unix_unlink_stale(path, 64);
+	if (server->fd == -1) {
+		if (errno == EADDRINUSE)
+			i_fatal("Socket already exists: %s", path);
+		else
 			i_fatal("net_listen_unix(%s) failed: %m", path);
-
-		/* see if it really exists */
-		if (net_connect_unix(path) != -1 || errno != ECONNREFUSED)
-			i_fatal("Socket already exists: %s", path);
-
-		/* delete and try again */
-		if (unlink(path) < 0)
-			i_fatal("unlink(%s) failed: %m", path);
 	}
 
 	server->io = io_add(server->fd, IO_READ,
diff -r 2df7a88a5458 -r ec83f6dcb585 src/lib/network.c
--- a/src/lib/network.c	Wed Sep 24 23:33:59 2008 +0300
+++ b/src/lib/network.c	Sat Sep 27 12:20:26 2008 +0300
@@ -395,6 +395,33 @@ int net_listen_unix(const char *path, in
 	return -1;
 }
 
+int net_listen_unix_unlink_stale(const char *path, int backlog)
+{
+	unsigned int i = 0;
+	int fd;
+
+	while ((fd = net_listen_unix(path, backlog)) == -1) {
+		if (errno != EADDRINUSE || ++i == 2)
+			return -1;
+
+		/* see if it really exists */
+		fd = net_connect_unix(path);
+		if (fd != -1 || errno != ECONNREFUSED) {
+			if (fd != -1) (void)close(fd);
+			errno = EADDRINUSE;
+			return -1;
+		}
+
+		/* delete and try again */
+		if (unlink(path) < 0 && errno != ENOENT) {
+			i_error("unlink(%s) failed: %m", path);
+			errno = EADDRINUSE;
+			return -1;
+		}
+	}
+	return fd;
+}
+
 int net_accept(int fd, struct ip_addr *addr, unsigned int *port)
 {
 	union sockaddr_union so;
diff -r 2df7a88a5458 -r ec83f6dcb585 src/lib/network.h
--- a/src/lib/network.h	Wed Sep 24 23:33:59 2008 +0300
+++ b/src/lib/network.h	Sat Sep 27 12:20:26 2008 +0300
@@ -67,6 +67,10 @@ int net_listen(const struct ip_addr *my_
 int net_listen(const struct ip_addr *my_ip, unsigned int *port, int backlog);
 /* Listen for connections on an UNIX socket */
 int net_listen_unix(const char *path, int backlog);
+/* Like net_listen_unix(), but if socket already exists, try to connect to it.
+   If it fails with ECONNREFUSED, unlink the socket and try creating it
+   again. */
+int net_listen_unix_unlink_stale(const char *path, int backlog);
 /* Accept a connection on a socket. Returns -1 if the connection got closed,
    -2 for other failures */
 int net_accept(int fd, struct ip_addr *addr, unsigned int *port);
diff -r 2df7a88a5458 -r ec83f6dcb585 src/lib/unix-socket-create.c
--- a/src/lib/unix-socket-create.c	Wed Sep 24 23:33:59 2008 +0300
+++ b/src/lib/unix-socket-create.c	Sat Sep 27 12:20:26 2008 +0300
@@ -13,10 +13,8 @@ int unix_socket_create(const char *path,
 	mode_t old_umask;
 	int fd;
 
-	(void)unlink(path);
-
 	old_umask = umask(0777 ^ mode);
-	fd = net_listen_unix(path, backlog);
+	fd = net_listen_unix_unlink_stale(path, backlog);
 	umask(old_umask);
 
 	if (fd < 0) {
diff -r 2df7a88a5458 -r ec83f6dcb585 src/master/dict-process.c
--- a/src/master/dict-process.c	Wed Sep 24 23:33:59 2008 +0300
+++ b/src/master/dict-process.c	Sat Sep 27 12:20:26 2008 +0300
@@ -114,37 +114,17 @@ static int dict_process_listen(struct di
 static int dict_process_listen(struct dict_process *process)
 {
 	mode_t old_umask;
-	int fd, i = 0;
 
-	for (;;) {
-		old_umask = umask(0);
-		process->fd = net_listen_unix(process->path, 64);
-		umask(old_umask);
-
-		if (process->fd != -1)
-			break;
-
-		if (errno != EADDRINUSE || ++i == 2) {
-			i_error("net_listen_unix(%s) failed: %m",
-				process->path);
-			return -1;
-		}
-
-		/* see if it really exists */
-		fd = net_connect_unix(process->path);
-		if (fd != -1 || errno != ECONNREFUSED) {
-			if (fd != -1) (void)close(fd);
+	old_umask = umask(0);
+	process->fd = net_listen_unix_unlink_stale(process->path, 64);
+	umask(old_umask);
+	if (process->fd == -1) {
+		if (errno == EADDRINUSE)
 			i_error("Socket already exists: %s", process->path);
-			return -1;
-		}
-
-		/* delete and try again */
-		if (unlink(process->path) < 0 && errno != ENOENT) {
-			i_error("unlink(%s) failed: %m", process->path);
-			return -1;
-		}
+		else
+			i_error("net_listen_unix(%s) failed: %m", process->path);
+		return -1;
 	}
-
 	fd_close_on_exec(process->fd, TRUE);
 	process->io = io_add(process->fd, IO_READ,
 			     dict_process_listen_input, process);


More information about the dovecot-cvs mailing list