[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[GNUnet-SVN] r11900 - in gnunet/src: include util
From: |
gnunet |
Subject: |
[GNUnet-SVN] r11900 - in gnunet/src: include util |
Date: |
Wed, 23 Jun 2010 13:58:33 +0200 |
Author: grothoff
Date: 2010-06-23 13:58:33 +0200 (Wed, 23 Jun 2010)
New Revision: 11900
Modified:
gnunet/src/include/gnunet_network_lib.h
gnunet/src/include/gnunet_server_lib.h
gnunet/src/util/network.c
gnunet/src/util/server.c
gnunet/src/util/service.c
Log:
support for systemd style listen fd passing
Modified: gnunet/src/include/gnunet_network_lib.h
===================================================================
--- gnunet/src/include/gnunet_network_lib.h 2010-06-23 11:41:46 UTC (rev
11899)
+++ gnunet/src/include/gnunet_network_lib.h 2010-06-23 11:58:33 UTC (rev
11900)
@@ -72,6 +72,16 @@
/**
+ * Box a native socket (and check that it is a socket).
+ *
+ * @param fd socket to box
+ * @return NULL on error (including not supported on target platform)
+ */
+struct GNUNET_NETWORK_Handle *
+GNUNET_NETWORK_socket_box_native (int fd);
+
+
+/**
* Bind to a connected socket
*
* @param desc socket to bind
Modified: gnunet/src/include/gnunet_server_lib.h
===================================================================
--- gnunet/src/include/gnunet_server_lib.h 2010-06-23 11:41:46 UTC (rev
11899)
+++ gnunet/src/include/gnunet_server_lib.h 2010-06-23 11:58:33 UTC (rev
11900)
@@ -114,6 +114,29 @@
* @param sched scheduler to use
* @param access function for access control
* @param access_cls closure for access
+ * @param lsocks NULL-terminated array of listen sockets
+ * @param maxbuf maximum write buffer size for accepted sockets
+ * @param idle_timeout after how long should we timeout idle connections?
+ * @param require_found if YES, connections sending messages of unknown type
+ * will be closed
+ * @return handle for the new server, NULL on error
+ * (typically, "port" already in use)
+ */
+struct GNUNET_SERVER_Handle *
+GNUNET_SERVER_create_with_sockets (struct GNUNET_SCHEDULER_Handle *sched,
+ GNUNET_CONNECTION_AccessCheck access, void
*access_cls,
+ struct GNUNET_NETWORK_Handle **lsocks,
+ size_t maxbuf,
+ struct GNUNET_TIME_Relative
+ idle_timeout,
+ int require_found);
+
+/**
+ * Create a new server.
+ *
+ * @param sched scheduler to use
+ * @param access function for access control
+ * @param access_cls closure for access
* @param serverAddr address toes listen on (including port), NULL terminated
array
* @param socklen lengths of respective serverAddr
* @param maxbuf maximum write buffer size for accepted sockets
Modified: gnunet/src/util/network.c
===================================================================
--- gnunet/src/util/network.c 2010-06-23 11:41:46 UTC (rev 11899)
+++ gnunet/src/util/network.c 2010-06-23 11:58:33 UTC (rev 11900)
@@ -308,6 +308,29 @@
/**
+ * Box a native socket (and check that it is a socket).
+ *
+ * @param fd socket to box
+ * @return NULL on error (including not supported on target platform)
+ */
+struct GNUNET_NETWORK_Handle *
+GNUNET_NETWORK_socket_box_native (int fd)
+{
+#if MINGW
+ return NULL;
+#else
+ struct GNUNET_NETWORK_Handle *ret;
+
+ if (fcntl (fd, F_GETFD) < 0)
+ return NULL; /* invalid FD */
+ ret = GNUNET_malloc (sizeof (struct GNUNET_NETWORK_Handle));
+ ret->fd = fd;
+ return ret;
+#endif
+}
+
+
+/**
* Connect a socket
* @param desc socket
* @param address peer address
Modified: gnunet/src/util/server.c
===================================================================
--- gnunet/src/util/server.c 2010-06-23 11:41:46 UTC (rev 11899)
+++ gnunet/src/util/server.c 2010-06-23 11:58:33 UTC (rev 11900)
@@ -395,6 +395,60 @@
* @param sched scheduler to use
* @param access function for access control
* @param access_cls closure for access
+ * @param lsocks NULL-terminated array of listen sockets
+ * @param maxbuf maximum write buffer size for accepted sockets
+ * @param idle_timeout after how long should we timeout idle connections?
+ * @param require_found if YES, connections sending messages of unknown type
+ * will be closed
+ * @return handle for the new server, NULL on error
+ * (typically, "port" already in use)
+ */
+struct GNUNET_SERVER_Handle *
+GNUNET_SERVER_create_with_sockets (struct GNUNET_SCHEDULER_Handle *sched,
+ GNUNET_CONNECTION_AccessCheck access, void
*access_cls,
+ struct GNUNET_NETWORK_Handle **lsocks,
+ size_t maxbuf,
+ struct GNUNET_TIME_Relative
+ idle_timeout,
+ int require_found)
+{
+ struct GNUNET_SERVER_Handle *ret;
+ struct GNUNET_NETWORK_FDSet *r;
+ int i;
+
+ ret = GNUNET_malloc (sizeof (struct GNUNET_SERVER_Handle));
+ ret->sched = sched;
+ ret->maxbuf = maxbuf;
+ ret->idle_timeout = idle_timeout;
+ ret->listen_sockets = lsocks;
+ ret->access = access;
+ ret->access_cls = access_cls;
+ ret->require_found = require_found;
+ if (lsocks != NULL)
+ {
+ r = GNUNET_NETWORK_fdset_create ();
+ i = 0;
+ while (NULL != ret->listen_sockets[i])
+ GNUNET_NETWORK_fdset_set (r, ret->listen_sockets[i++]);
+ ret->listen_task = GNUNET_SCHEDULER_add_select (sched,
+
GNUNET_SCHEDULER_PRIORITY_HIGH,
+ GNUNET_SCHEDULER_NO_TASK,
+
GNUNET_TIME_UNIT_FOREVER_REL,
+ r, NULL,
+ &process_listen_socket,
+ ret);
+ GNUNET_NETWORK_fdset_destroy (r);
+ }
+ return ret;
+}
+
+
+/**
+ * Create a new server.
+ *
+ * @param sched scheduler to use
+ * @param access function for access control
+ * @param access_cls closure for access
* @param serverAddr address to listen on (including port), NULL terminated
array
* @param socklen length of serverAddr
* @param maxbuf maximum write buffer size for accepted sockets
@@ -414,9 +468,7 @@
struct GNUNET_TIME_Relative
idle_timeout, int require_found)
{
- struct GNUNET_SERVER_Handle *ret;
struct GNUNET_NETWORK_Handle **lsocks;
- struct GNUNET_NETWORK_FDSet *r;
unsigned int i;
unsigned int j;
@@ -448,30 +500,12 @@
{
lsocks = NULL;
}
- ret = GNUNET_malloc (sizeof (struct GNUNET_SERVER_Handle));
- ret->sched = sched;
- ret->maxbuf = maxbuf;
- ret->idle_timeout = idle_timeout;
- ret->listen_sockets = lsocks;
- ret->access = access;
- ret->access_cls = access_cls;
- ret->require_found = require_found;
- if (lsocks != NULL)
- {
- r = GNUNET_NETWORK_fdset_create ();
- i = 0;
- while (NULL != ret->listen_sockets[i])
- GNUNET_NETWORK_fdset_set (r, ret->listen_sockets[i++]);
- ret->listen_task = GNUNET_SCHEDULER_add_select (sched,
-
GNUNET_SCHEDULER_PRIORITY_HIGH,
- GNUNET_SCHEDULER_NO_TASK,
-
GNUNET_TIME_UNIT_FOREVER_REL,
- r, NULL,
- &process_listen_socket,
- ret);
- GNUNET_NETWORK_fdset_destroy (r);
- }
- return ret;
+ return GNUNET_SERVER_create_with_sockets (sched,
+ access, access_cls,
+ lsocks,
+ maxbuf,
+ idle_timeout,
+ require_found);
}
Modified: gnunet/src/util/service.c
===================================================================
--- gnunet/src/util/service.c 2010-06-23 11:41:46 UTC (rev 11899)
+++ gnunet/src/util/service.c 2010-06-23 11:58:33 UTC (rev 11900)
@@ -435,7 +435,8 @@
struct GNUNET_SCHEDULER_Handle *sched;
/**
- * NULL-terminated array of addresses to bind to.
+ * NULL-terminated array of addresses to bind to, NULL if we got pre-bound
+ * listen sockets.
*/
struct sockaddr **addrs;
@@ -483,6 +484,16 @@
struct GNUNET_SERVER_MessageHandler *my_handlers;
/**
+ * Array of the lengths of the entries in addrs.
+ */
+ socklen_t * addrlens;
+
+ /**
+ * NULL-terminated array of listen sockets we should take over.
+ */
+ struct GNUNET_NETWORK_Handle **lsocks;
+
+ /**
* Idle timeout for server.
*/
struct GNUNET_TIME_Relative timeout;
@@ -515,11 +526,6 @@
*/
enum GNUNET_SERVICE_Options options;
- /**
- * Array of the lengths of the entries in addrs.
- */
- socklen_t * addrlens;
-
};
@@ -1085,6 +1091,11 @@
unsigned long long maxbuf;
struct GNUNET_TIME_Relative idleout;
int tolerant;
+ const char *lpid;
+ unsigned int pid;
+ const char *nfds;
+ unsigned int cnt;
+ int flags;
if (GNUNET_CONFIGURATION_have_value (sctx->cfg,
sctx->serviceName, "TIMEOUT"))
@@ -1140,11 +1151,45 @@
else
tolerant = GNUNET_NO;
- if (GNUNET_SYSERR ==
- GNUNET_SERVICE_get_server_addresses (sctx->serviceName,
- sctx->cfg,
- &sctx->addrs,
- &sctx->addrlens))
+#ifndef MINGW
+ errno = 0;
+ if ( (NULL != (lpid = getenv ("LISTEN_PID"))) &&
+ (1 == sscanf ("%u", lpid, &pid)) &&
+ (getpid () == (pid_t) pid) &&
+ (NULL != (nfds = getenv ("LISTEN_FDS"))) &&
+ (1 == sscanf ("%u", nfds, &cnt)) &&
+ (cnt > 0) )
+ {
+ sctx->lsocks = GNUNET_malloc (sizeof(struct GNUNET_NETWORK_Handle*) *
(cnt+1));
+ while (0 < cnt--)
+ {
+ flags = fcntl (3 + cnt, F_GETFD);
+ if ( (flags < 0) ||
+ (0 != (flags & FD_CLOEXEC)) ||
+ (NULL == (sctx->lsocks[cnt] = GNUNET_NETWORK_socket_box_native
(3 + cnt))) )
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
+ _("Could not access pre-bound socket %u, will try to
bind myself\n"),
+ (unsigned int) 3 +cnt);
+ cnt++;
+ while (sctx->lsocks[cnt] != NULL)
+ GNUNET_NETWORK_socket_close (sctx->lsocks[cnt++]);
+ GNUNET_free (sctx->lsocks);
+ sctx->lsocks = NULL;
+ break;
+ }
+ }
+ unsetenv ("LISTEN_PID");
+ unsetenv ("LISTEN_FDS");
+ }
+#endif
+
+ if ( (sctx->lsocks == NULL) &&
+ (GNUNET_SYSERR ==
+ GNUNET_SERVICE_get_server_addresses (sctx->serviceName,
+ sctx->cfg,
+ &sctx->addrs,
+ &sctx->addrlens)) )
return GNUNET_SYSERR;
sctx->require_found = tolerant ? GNUNET_NO : GNUNET_YES;
sctx->maxbuf = (size_t) maxbuf;
@@ -1265,23 +1310,34 @@
unsigned int i;
sctx->sched = tc->sched;
- sctx->server = GNUNET_SERVER_create (tc->sched,
- &check_access,
- sctx,
- sctx->addrs,
- sctx->addrlens,
- sctx->maxbuf,
- sctx->timeout, sctx->require_found);
+ if (sctx->lsocks != NULL)
+ sctx->server = GNUNET_SERVER_create_with_sockets (tc->sched,
+ &check_access,
+ sctx,
+ sctx->lsocks,
+ sctx->maxbuf,
+ sctx->timeout,
sctx->require_found);
+ else
+ sctx->server = GNUNET_SERVER_create (tc->sched,
+ &check_access,
+ sctx,
+ sctx->addrs,
+ sctx->addrlens,
+ sctx->maxbuf,
+ sctx->timeout, sctx->require_found);
if (sctx->server == NULL)
{
- i = 0;
- while (sctx->addrs[i] != NULL)
+ if (sctx->addrs != NULL)
{
- GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- _("Failed to start `%s' at `%s'\n"),
- sctx->serviceName,
- GNUNET_a2s (sctx->addrs[i], sctx->addrlens[i]));
- i++;
+ i = 0;
+ while (sctx->addrs[i] != NULL)
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ _("Failed to start `%s' at `%s'\n"),
+ sctx->serviceName,
+ GNUNET_a2s (sctx->addrs[i], sctx->addrlens[i]));
+ i++;
+ }
}
sctx->ret = GNUNET_SYSERR;
return;
@@ -1307,14 +1363,17 @@
sctx->ready_confirm_fd = -1;
write_pid_file (sctx, getpid ());
}
- i = 0;
- while (sctx->addrs[i] != NULL)
+ if (sctx->addrs != NULL)
{
- GNUNET_log (GNUNET_ERROR_TYPE_INFO,
- _("Service `%s' runs at %s\n"),
- sctx->serviceName,
- GNUNET_a2s (sctx->addrs[i], sctx->addrlens[i]));
- i++;
+ i = 0;
+ while (sctx->addrs[i] != NULL)
+ {
+ GNUNET_log (GNUNET_ERROR_TYPE_INFO,
+ _("Service `%s' runs at %s\n"),
+ sctx->serviceName,
+ GNUNET_a2s (sctx->addrs[i], sctx->addrlens[i]));
+ i++;
+ }
}
sctx->task (sctx->task_cls, tc->sched, sctx->server, sctx->cfg);
}
@@ -1594,19 +1653,33 @@
sctx->sched = sched;
/* setup subsystems */
- if ((GNUNET_OK != setup_service (sctx)) ||
- (NULL == (sctx->server = GNUNET_SERVER_create (sched,
- &check_access,
- sctx,
- sctx->addrs,
- sctx->addrlens,
- sctx->maxbuf,
- sctx->timeout,
- sctx->require_found))))
+ if (GNUNET_OK != setup_service (sctx))
{
GNUNET_SERVICE_stop (sctx);
return NULL;
}
+ if (sctx->lsocks != NULL)
+ sctx->server = GNUNET_SERVER_create_with_sockets (sched,
+ &check_access,
+ sctx,
+ sctx->lsocks,
+ sctx->maxbuf,
+ sctx->timeout,
sctx->require_found);
+ else
+ sctx->server = GNUNET_SERVER_create (sched,
+ &check_access,
+ sctx,
+ sctx->addrs,
+ sctx->addrlens,
+ sctx->maxbuf,
+ sctx->timeout,
+ sctx->require_found);
+
+ if (NULL == sctx->server)
+ {
+ GNUNET_SERVICE_stop (sctx);
+ return NULL;
+ }
sctx->my_handlers = GNUNET_malloc (sizeof (defhandlers));
memcpy (sctx->my_handlers, defhandlers, sizeof (defhandlers));
i = 0;
@@ -1642,10 +1715,13 @@
if (NULL != sctx->server)
GNUNET_SERVER_destroy (sctx->server);
GNUNET_free_non_null (sctx->my_handlers);
- i = 0;
- while (sctx->addrs[i] != NULL)
- GNUNET_free (sctx->addrs[i++]);
- GNUNET_free (sctx->addrs);
+ if (sctx->addrs != NULL)
+ {
+ i = 0;
+ while (sctx->addrs[i] != NULL)
+ GNUNET_free (sctx->addrs[i++]);
+ GNUNET_free (sctx->addrs);
+ }
GNUNET_free_non_null (sctx->addrlens);
GNUNET_free_non_null (sctx->v4_denied);
GNUNET_free_non_null (sctx->v6_denied);
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [GNUnet-SVN] r11900 - in gnunet/src: include util,
gnunet <=