speechd-discuss
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH 08/10] Use launchd on OS X for launching the server


From: Boris Dušek
Subject: [PATCH 08/10] Use launchd on OS X for launching the server
Date: Mon, 23 Jul 2012 15:22:33 +0200

From: Boris Dus?ek <address@hidden>
To: address@hidden

---
 .gitignore                                         |    1 +
 .../org.freebsoft.speech-dispatcher.plist.in       |   21 +++++++++
 configure.ac                                       |    1 +
 src/api/c/libspeechd.c                             |    3 +
 src/api/python/speechd/client.py                   |    2 +
 src/server/options.c                               |   12 +++++
 src/server/options.h                               |    4 ++
 src/server/speechd.c                               |   46 ++++++++++++++++++++
 8 files changed, 90 insertions(+), 0 deletions(-)
 create mode 100644 config/launchd/org.freebsoft.speech-dispatcher.plist.in

diff --git a/.gitignore b/.gitignore
index b479803..0117aa9 100644
--- a/.gitignore
+++ b/.gitignore
@@ -17,3 +17,4 @@ libtool
 py-compile
 speech-dispatcher.pc
 stamp-h1
+org.freebsoft.speech-dispatcher-session.plist
diff --git a/config/launchd/org.freebsoft.speech-dispatcher.plist.in 
b/config/launchd/org.freebsoft.speech-dispatcher.plist.in
new file mode 100644
index 0000000..5d6a2d0
--- /dev/null
+++ b/config/launchd/org.freebsoft.speech-dispatcher.plist.in
@@ -0,0 +1,21 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<plist version="1.0">
+    <dict>
+        <key>Label</key>
+        <string>org.freebsoft.speech-dispatcher-session</string>
+
+        <key>ProgramArguments</key>
+        <array>
+            <string>@prefix@/bin/speech-dispatcher</string>
+        </array>
+
+        <key>Sockets</key>
+        <dict>
+            <key>spd_server_socket</key>
+            <dict>
+                <key>SecureSocketWithKey</key>
+                <string>SPEECHD_ADDRESS</string>
+            </dict>
+        </dict>
+    </dict>
+</plist>
diff --git a/configure.ac b/configure.ac
index af45549..2d1bfbd 100644
--- a/configure.ac
+++ b/configure.ac
@@ -362,6 +362,7 @@ AC_CONFIG_FILES([Makefile
                  speech-dispatcher.pc
                  config/Makefile
                  config/clients/Makefile
+                 config/launchd/org.freebsoft.speech-dispatcher.plist
                  config/modules/Makefile
                  doc/Makefile
                  include/Makefile
diff --git a/src/api/c/libspeechd.c b/src/api/c/libspeechd.c
index 2b26ba4..6d505f9 100644
--- a/src/api/c/libspeechd.c
+++ b/src/api/c/libspeechd.c
@@ -176,6 +176,9 @@ SPDConnectionAddress *spd_get_default_address(char **error)
        if (env_address == NULL) {      // Default method = unix sockets
                address->method = SPD_METHOD_UNIX_SOCKET;
                address->unix_socket_name = _get_default_unix_socket_name();
+       } else if (env_address[0] == '/') {
+               address->method = SPD_METHOD_UNIX_SOCKET;
+               address->unix_socket_name = strdup(env_address);
        } else {
                pa = g_strsplit(env_address, ":", 0);
                assert(pa);
diff --git a/src/api/python/speechd/client.py b/src/api/python/speechd/client.py
index 8d34363..4bcaf85 100644
--- a/src/api/python/speechd/client.py
+++ b/src/api/python/speechd/client.py
@@ -549,6 +549,8 @@ class SSIPClient(object):
         _address = address or os.environ.get("SPEECHD_ADDRESS")        
 
         if _address:
+            if _address[0]='/':
+                _address = '%s:%s' % (CommunicationMethod.UNIX_SOCKET, 
_address,)
             
connection_args.update(self._connection_arguments_from_address(_address))
         # Respect the old (deprecated) key arguments and environment variables
         # TODO: Remove this section in 0.8 release
diff --git a/src/server/options.c b/src/server/options.c
index 50de1e1..8428643 100644
--- a/src/server/options.c
+++ b/src/server/options.c
@@ -37,14 +37,18 @@
 #include <i18n.h>
 
 static const struct option spd_long_options[] = {
+#ifndef HAVE_LAUNCHD
        {"run-daemon", 0, 0, 'd'},
        {"run-single", 0, 0, 's'},
        {"spawn", 0, 0, 'a'},
+#endif
        {"log-level", 1, 0, 'l'},
        {"log-dir", required_argument, 0, 'L'},
+#ifndef HAVE_LAUNCHD
        {"communication-method", 1, 0, 'c'},
        {"socket-path", 1, 0, 'S'},
        {"port", 1, 0, 'p'},
+#endif
        {"pid-file", 1, 0, 'P'},
        {"config-dir", required_argument, 0, 'C'},
        {"version", 0, 0, 'v'},
@@ -53,7 +57,11 @@ static const struct option spd_long_options[] = {
        {0, 0, 0, 0}
 };
 
+#ifndef HAVE_LAUNCHD
 static const char *const spd_short_options = "dsal:L:c:S:p:P:C:vDh";
+#else
+static const char *const spd_short_options = "l:L:P:C:vDh";
+#endif
 
 void options_print_help(char *argv[])
 {
@@ -66,16 +74,19 @@ void options_print_help(char *argv[])
             argv[0]);
        printf(_("%s -- Common interface for Speech Synthesis %s\n\n"),
               "Speech Dispatcher", "(GNU GPL)");
+#ifndef HAVE_LAUNCHD
        printf("-d, --run-daemon\t");
        printf(_("Run as a daemon\n"));
        printf("-s, --run-single\t");
        printf(_("Run as single application\n"));
        printf("-a, --spawn\t\t");
        printf(_("Start only if autospawn is not disabled\n"));
+#endif
        printf("-l, --log-level\t\t");
        printf(_("Set log level (between %d and %d)\n"), 1, 5);
        printf("-L, --log-dir\t\t");
        printf(_("Set path to logging\n"));
+#ifndef HAVE_LAUNCHD
        printf("-c, --communication-method\t");
        printf(_("Communication method to use ('%s' or '%s')\n"), "unix_socket",
               "inet_socket");
@@ -85,6 +96,7 @@ void options_print_help(char *argv[])
               "unix_socket", "default");
        printf("-p, --port\t\t");
        printf(_("Specify a port number for '%s' method\n"), "inet_socket");
+#endif
        printf("-P, --pid-file\t\t");
        printf(_("Set path to pid file\n"));
        printf("-C, --config-dir\t");
diff --git a/src/server/options.h b/src/server/options.h
index 870502e..9124369 100644
--- a/src/server/options.h
+++ b/src/server/options.h
@@ -26,3 +26,7 @@
 void options_print_help(char *argv[]);
 void options_print_version(void);
 void options_parse(int argc, char *argv[]);
+
+#ifdef __APPLE__
+#define HAVE_LAUNCHD 1
+#endif
diff --git a/src/server/speechd.c b/src/server/speechd.c
index be6e4c9..4f02d38 100644
--- a/src/server/speechd.c
+++ b/src/server/speechd.c
@@ -48,6 +48,10 @@
 
 #include <i18n.h>
 
+#ifdef HAVE_LAUNCHD
+#include <launch.h>
+#endif
+
 /* list of output modules */
 GList *output_modules;
 
@@ -922,10 +926,14 @@ int main(int argc, char *argv[])
        fd_set testfds;
        int fd;
        int ret;
+#ifdef HAVE_LAUNCHD
+       launch_data_t launch_data, launch_resp, launch_start;
+#else
        /* Autospawn helper variables */
        char *spawn_communication_method = NULL;
        int spawn_port = 0;
        char *spawn_socket_path = NULL;
+#endif
 
        /* Initialize threading and thread safety in Glib */
        g_thread_init(NULL);
@@ -946,6 +954,7 @@ int main(int argc, char *argv[])
 
        options_parse(argc, argv);
 
+#ifndef HAVE_LAUNCHD
        if (SpeechdOptions.spawn) {
                /* In case of --spawn, copy the host port and socket_path
                   parameters into temporary spawn_ variables for later 
comparison
@@ -967,6 +976,7 @@ int main(int argc, char *argv[])
                        SpeechdOptions.socket_path_set = 0;
                }
        }
+#endif
 
        MSG(1, "Speech Dispatcher " VERSION " starting");
 
@@ -1013,6 +1023,7 @@ int main(int argc, char *argv[])
        if (create_pid_file() != 0)
                exit(1);
 
+#ifndef HAVE_LAUNCHD
        /* Handle --spawn request */
        if (SpeechdOptions.spawn) {
                /* Check whether spawning is not disabled */
@@ -1041,6 +1052,7 @@ int main(int argc, char *argv[])
                g_regex_unref(regexp);
                MSG(2, "Starting Speech Dispatcher due to auto-spawn");
        }
+#endif
 
        /* Initialize logging mutex to workaround ctime threading bug */
        /* Must be done no later than here */
@@ -1058,6 +1070,7 @@ int main(int argc, char *argv[])
 
        speechd_init();
 
+#ifndef HAVE_LAUNCHD
        /* Handle socket_path 'default' */
        // TODO: This is a hack, we should do that at appropriate places...
        if (!strcmp(SpeechdOptions.socket_path, "default")) {
@@ -1159,7 +1172,39 @@ int main(int argc, char *argv[])
        } else {
                FATAL("Unknown communication method");
        }
+#else
+       launch_start = launch_data_new_string(LAUNCH_KEY_CHECKIN);
+       if (NULL == (launch_resp = launch_msg(launch_start))) {
+               MSG(1, "launchd check-in failed: %s", strerror(errno));
+               FATAL("launchd check-in failed");
+       } else {
+               if (LAUNCH_DATA_ERRNO == launch_data_get_type(launch_resp)) {
+                       errno = launch_data_get_errno(launch_resp);
+                       MSG(1, "launchd check-in failed: %s", strerror(errno));
+                       FATAL("launchd check-in failed");
+               }
+               if (NULL == (launch_data = launch_data_dict_lookup(launch_resp, 
LAUNCH_JOBKEY_SOCKETS))) {
+                       FATAL("No socket to listen on");
+               }
+               if (1 != (launch_data_dict_get_count(launch_data))) {
+                       FATAL("Exactly one socket must be specified in the 
launchd configuration file");
+               }
+               if (NULL == (launch_data = launch_data_dict_lookup(launch_data, 
"spd_server_socket"))) {
+                       FATAL("Did not find spd_server_socket in launchd 
configuration");
+               }
+               if (1 != launch_data_array_get_count(launch_data)) {
+                       FATAL("Exactly one socket must be specified in the 
launchd configuration file");
+               }
+               if (NULL == (launch_data = 
launch_data_array_get_index(launch_data, 0))) {
+                       FATAL("launchd: Could not get the one and only one 
socket from configuration");
+               }
+               server_socket = launch_data_get_fd(launch_data);
+               launch_data_free(launch_resp);
+       }
+       launch_data_free(launch_start);
+#endif
 
+#ifndef HAVE_LAUNCHD
        /* Fork, set uid, chdir, etc. */
        if (spd_mode == SPD_MODE_DAEMON) {
                if (daemon(0, 0)) {
@@ -1170,6 +1215,7 @@ int main(int argc, char *argv[])
                if (create_pid_file() == -1)
                        return -1;
        }
+#endif
 
        MSG(4, "Creating new thread for speak()");
        ret = pthread_create(&speak_thread, NULL, speak, NULL);
-- 
1.7.7.5 (Apple Git-26)




reply via email to

[Prev in Thread] Current Thread [Next in Thread]