diff options
author | Matthieu Herrb <matthieu.herrb@laas.fr> | 2014-02-09 08:49:36 +0100 |
---|---|---|
committer | Matthieu Herrb <matthieu.herrb@laas.fr> | 2014-02-09 08:49:36 +0100 |
commit | 69579512bc9f7a4b1d4c52999a73b59a4e37300c (patch) | |
tree | e693803786688d1e386111c1b25a6d21c6560635 | |
parent | 54787d6595083b9fd3e4dd220febe17821a1438c (diff) | |
parent | 3f0de269abe59353acbd7a5587d68ce0da91db67 (diff) |
Merge remote-tracking branch 'origin/master' into obsd
-rw-r--r-- | Xtrans.c | 127 | ||||
-rw-r--r-- | Xtrans.h | 8 | ||||
-rw-r--r-- | Xtransint.h | 1 | ||||
-rw-r--r-- | configure.ac | 2 |
4 files changed, 136 insertions, 2 deletions
@@ -48,6 +48,10 @@ from The Open Group. */ #include <ctype.h> +#ifdef HAVE_SYSTEMD_DAEMON +#include <string.h> +#include <systemd/sd-daemon.h> +#endif /* * The transport table contains a definition for every transport (protocol) @@ -747,6 +751,34 @@ TRANS(CreateListener) (XtransConnInfo ciptr, char *port, unsigned int flags) } int +TRANS(Received) (const char * protocol) + +{ + Xtransport *trans; + int i = 0, ret = 0; + + prmsg (5, "Received(%s)\n", protocol); + + if ((trans = TRANS(SelectTransport)(protocol)) == NULL) + { + prmsg (1,"Received: unable to find transport: %s\n", + protocol); + + return -1; + } + if (trans->flags & TRANS_ALIAS) { + if (trans->nolisten) + while (trans->nolisten[i]) { + ret |= TRANS(Received)(trans->nolisten[i]); + i++; + } + } + + trans->flags |= TRANS_RECEIVED; + return ret; +} + +int TRANS(NoListen) (const char * protocol) { @@ -773,6 +805,22 @@ TRANS(NoListen) (const char * protocol) } int +TRANS(IsListening) (const char * protocol) +{ + Xtransport *trans; + + if ((trans = TRANS(SelectTransport)(protocol)) == NULL) + { + prmsg (1,"TransIsListening: unable to find transport: %s\n", + protocol); + + return 0; + } + + return !(trans->flags & TRANS_NOLISTEN); +} + +int TRANS(ResetListener) (XtransConnInfo ciptr) { @@ -1026,6 +1074,79 @@ complete_network_count (void) } +static int +receive_listening_fds(char* port, XtransConnInfo* temp_ciptrs, int* count_ret) + +{ +#ifdef HAVE_SYSTEMD_DAEMON + XtransConnInfo ciptr; + int i, systemd_listen_fds; + + systemd_listen_fds = sd_listen_fds(1); + if (systemd_listen_fds < 0) + { + prmsg (1, "receive_listening_fds: sd_listen_fds error: %s\n", + strerror(-systemd_listen_fds)); + return -1; + } + + for (i = 0; i < systemd_listen_fds && *count_ret < NUMTRANS; i++) + { + struct sockaddr_storage a; + int ti; + const char* tn; + socklen_t al; + + al = sizeof(a); + if (getsockname(i + SD_LISTEN_FDS_START, (struct sockaddr*)&a, &al) < 0) { + prmsg (1, "receive_listening_fds: getsockname error: %s\n", + strerror(errno)); + return -1; + } + + switch (a.ss_family) + { + case AF_UNIX: + ti = TRANS_SOCKET_UNIX_INDEX; + if (*((struct sockaddr_un*)&a)->sun_path == '\0' && + al > sizeof(sa_family_t)) + tn = "local"; + else + tn = "unix"; + break; + case AF_INET: + ti = TRANS_SOCKET_INET_INDEX; + tn = "inet"; + break; +#if defined(IPv6) && defined(AF_INET6) + case AF_INET6: + ti = TRANS_SOCKET_INET6_INDEX; + tn = "inet6"; + break; +#endif /* IPv6 */ + default: + prmsg (1, "receive_listening_fds:" + "Got unknown socket address family\n"); + return -1; + } + + ciptr = TRANS(ReopenCOTSServer)(ti, i + SD_LISTEN_FDS_START, port); + if (!ciptr) + { + prmsg (1, "receive_listening_fds:" + "Got NULL while trying to reopen socket received from systemd.\n"); + return -1; + } + + prmsg (5, "receive_listening_fds: received listener for %s, %d\n", + tn, ciptr->fd); + temp_ciptrs[(*count_ret)++] = ciptr; + TRANS(Received)(tn); + } +#endif /* HAVE_SYSTEMD_DAEMON */ + return 0; +} + #ifdef XQUARTZ_EXPORTS_LAUNCHD_FD extern int xquartz_launchd_fd; #endif @@ -1058,12 +1179,16 @@ TRANS(MakeAllCOTSServerListeners) (char *port, int *partial, int *count_ret, } #endif + if (receive_listening_fds(port, temp_ciptrs, count_ret) < 0) + return -1; + for (i = 0; i < NUMTRANS; i++) { Xtransport *trans = Xtransports[i].transport; unsigned int flags = 0; - if (trans->flags&TRANS_ALIAS || trans->flags&TRANS_NOLISTEN) + if (trans->flags&TRANS_ALIAS || trans->flags&TRANS_NOLISTEN || + trans->flags&TRANS_RECEIVED) continue; snprintf(buffer, sizeof(buffer), "%s/:%s", @@ -303,10 +303,18 @@ int TRANS(CreateListener)( unsigned int /* flags */ ); +int TRANS(Received) ( + const char* /* protocol*/ +); + int TRANS(NoListen) ( const char* /* protocol*/ ); +int TRANS(IsListening) ( + const char* /* protocol*/ +); + int TRANS(ResetListener)( XtransConnInfo /* ciptr */ ); diff --git a/Xtransint.h b/Xtransint.h index ec5a772..4c670b8 100644 --- a/Xtransint.h +++ b/Xtransint.h @@ -331,6 +331,7 @@ typedef struct _Xtransport_table { #define TRANS_NOUNLINK (1<<4) /* Don't unlink transport endpoints */ #define TRANS_ABSTRACT (1<<5) /* Use abstract sockets if available */ #define TRANS_NOXAUTH (1<<6) /* Don't verify authentication (because it's secure some other way at the OS layer) */ +#define TRANS_RECEIVED (1<<7) /* The fd for this has already been opened by someone else. */ /* Flags to preserve when setting others */ #define TRANS_KEEPFLAGS (TRANS_NOUNLINK|TRANS_ABSTRACT) diff --git a/configure.ac b/configure.ac index 998fb06..6898c6d 100644 --- a/configure.ac +++ b/configure.ac @@ -21,7 +21,7 @@ # Initialize Autoconf AC_PREREQ([2.60]) -AC_INIT([xtrans], [1.3.2], +AC_INIT([xtrans], [1.3.3], [https://bugs.freedesktop.org/enter_bug.cgi?product=xorg], [xtrans]) AC_CONFIG_SRCDIR([Makefile.am]) |