From f116b1282f8482dff6dc797f64270d95f79b53a3 Mon Sep 17 00:00:00 2001 From: Anders Carlsson Date: Sun, 16 Feb 2003 10:00:37 +0000 Subject: 2003-02-16 Anders Carlsson * bus/activation.c: (load_directory), (bus_activation_init), (bus_activation_activate_service): * bus/activation.h: * bus/driver.c: (bus_driver_handle_activate_service), (bus_driver_handle_message): More work on the activation handling. * dbus/dbus-errors.h: Add some error messages * dbus/dbus-message.c: (dbus_message_new_error_reply): * dbus/dbus-message.h: New function that creates an error message. * dbus/dbus-protocol.h: Add ACTIVATE_SERVER message. * dbus/dbus-server-unix.c: (unix_handle_watch), (_dbus_server_new_for_domain_socket): Call _dbus_fd_set_close_on_exec. * dbus/dbus-sysdeps.c: (make_pipe), (do_exec), (_dbus_spawn_async), (_dbus_disable_sigpipe), (_dbus_fd_set_close_on_exec): * dbus/dbus-sysdeps.h: Add _dbus_fd_set_close_on exec function. Also add function that checks that all open fds are set to close-on-exec and warns otherwise. * dbus/dbus-transport-unix.c: (_dbus_transport_new_for_domain_socket): Call _dbus_fd_set_close_on_exec. --- dbus/dbus-errors.h | 7 +++--- dbus/dbus-message.c | 44 +++++++++++++++++++++++++++++++++ dbus/dbus-message.h | 3 +++ dbus/dbus-protocol.h | 3 ++- dbus/dbus-server-unix.c | 3 +++ dbus/dbus-sysdeps.c | 61 ++++++++++++++++++++++++++++++---------------- dbus/dbus-transport-unix.c | 2 ++ 7 files changed, 98 insertions(+), 25 deletions(-) (limited to 'dbus') diff --git a/dbus/dbus-errors.h b/dbus/dbus-errors.h index 5cc77491..1b7b474a 100644 --- a/dbus/dbus-errors.h +++ b/dbus/dbus-errors.h @@ -49,9 +49,10 @@ struct DBusError void *padding1; /**< placeholder */ }; -#define DBUS_ERROR_SPAWN_FORK_FAILED "org.freedesktop.DBus.Error.Spawn.ForkFailed" -#define DBUS_ERROR_SPAWN_FAILED "org.freedesktop.DBus.Error.Spawn.Failed" -#define DBUS_ERROR_NO_MEMORY "org.freedesktop.DBus.Error.NoMemory" +#define DBUS_ERROR_ACTIVATE_SERVICE_NOT_FOUND "org.freedesktop.DBus.Activate.ServiceNotFound" +#define DBUS_ERROR_SPAWN_FORK_FAILED "org.freedesktop.DBus.Error.Spawn.ForkFailed" +#define DBUS_ERROR_SPAWN_FAILED "org.freedesktop.DBus.Error.Spawn.Failed" +#define DBUS_ERROR_NO_MEMORY "org.freedesktop.DBus.Error.NoMemory" typedef enum { diff --git a/dbus/dbus-message.c b/dbus/dbus-message.c index aca8c2cb..fced9c72 100644 --- a/dbus/dbus-message.c +++ b/dbus/dbus-message.c @@ -816,6 +816,50 @@ dbus_message_new_reply (DBusMessage *original_message) return message; } +/** + * Creates a new message that is an error reply to a certain message. + * + * @param original_message the original message + * @param error_name the error name + * @param error_message the error message string + * @returns a new error message + */ +DBusMessage* +dbus_message_new_error_reply (DBusMessage *original_message, + const char *error_name, + const char *error_message) +{ + DBusMessage *message; + const char *sender; + + sender = get_string_field (original_message, + FIELD_SENDER, NULL); + + _dbus_assert (sender != NULL); + + message = dbus_message_new (sender, error_name); + + if (message == NULL) + return NULL; + + if (!_dbus_message_set_reply_serial (message, + _dbus_message_get_client_serial (original_message))) + { + dbus_message_unref (message); + return NULL; + } + + if (!dbus_message_append_string (message, error_message)) + { + dbus_message_unref (message); + return NULL; + } + + dbus_message_set_is_error (message, TRUE); + + return message; +} + /** * Creates a new message that is an exact replica of the message * specified, except that its refcount is set to 1. diff --git a/dbus/dbus-message.h b/dbus/dbus-message.h index 82faf658..2038978b 100644 --- a/dbus/dbus-message.h +++ b/dbus/dbus-message.h @@ -39,6 +39,9 @@ typedef struct DBusMessageIter DBusMessageIter; DBusMessage* dbus_message_new (const char *service, const char *name); DBusMessage* dbus_message_new_reply (DBusMessage *original_message); +DBusMessage* dbus_message_new_error_reply (DBusMessage *original_message, + const char *error_name, + const char *error_message); DBusMessage *dbus_message_new_from_message (const DBusMessage *message); void dbus_message_ref (DBusMessage *message); diff --git a/dbus/dbus-protocol.h b/dbus/dbus-protocol.h index f043346a..dd9b3122 100644 --- a/dbus/dbus-protocol.h +++ b/dbus/dbus-protocol.h @@ -76,6 +76,7 @@ extern "C" { #define DBUS_SERVICE_REPLY_ALREADY_OWNER 0x8 /* Messages */ +#define DBUS_MESSAGE_ACTIVATE_SERVICE "org.freedesktop.DBus.ActivateService" #define DBUS_MESSAGE_SERVICE_EXISTS "org.freedesktop.DBus.ServiceExists" #define DBUS_MESSAGE_HELLO "org.freedesktop.DBus.Hello" #define DBUS_MESSAGE_LIST_SERVICES "org.freedesktop.DBus.ListServices" @@ -84,7 +85,7 @@ extern "C" { #define DBUS_MESSAGE_SERVICE_CREATED "org.freedesktop.DBus.ServiceCreated" #define DBUS_MESSAGE_SERVICE_DELETED "org.freedesktop.DBus.ServiceDeleted" #define DBUS_MESSAGE_SERVICE_LOST "org.freedesktop.DBus.ServiceLost" - + #define DBUS_MESSAGE_LOCAL_DISCONNECT "org.freedesktop.Local.Disconnect" #ifdef __cplusplus diff --git a/dbus/dbus-server-unix.c b/dbus/dbus-server-unix.c index 23bbdab3..6da70537 100644 --- a/dbus/dbus-server-unix.c +++ b/dbus/dbus-server-unix.c @@ -145,6 +145,7 @@ unix_handle_watch (DBusServer *server, } else { + _dbus_fd_set_close_on_exec (client_fd); handle_new_client_fd (server, client_fd); } } @@ -247,6 +248,8 @@ _dbus_server_new_for_domain_socket (const char *path, int listen_fd; listen_fd = _dbus_listen_unix_socket (path, result); + _dbus_fd_set_close_on_exec (listen_fd); + if (listen_fd < 0) return NULL; diff --git a/dbus/dbus-sysdeps.c b/dbus/dbus-sysdeps.c index 67677707..83b1f044 100644 --- a/dbus/dbus-sysdeps.c +++ b/dbus/dbus-sysdeps.c @@ -281,7 +281,7 @@ _dbus_connect_unix_socket (const char *path, struct sockaddr_un addr; fd = socket (AF_LOCAL, SOCK_STREAM, 0); - + if (fd < 0) { dbus_set_result (result, @@ -340,7 +340,7 @@ _dbus_listen_unix_socket (const char *path, struct sockaddr_un addr; listen_fd = socket (AF_LOCAL, SOCK_STREAM, 0); - + if (listen_fd < 0) { dbus_set_result (result, _dbus_result_from_errno (errno)); @@ -1490,7 +1490,11 @@ make_pipe (int p[2], return FALSE; } else - return TRUE; + { + _dbus_fd_set_close_on_exec (p[0]); + _dbus_fd_set_close_on_exec (p[1]); + return TRUE; + } } enum @@ -1563,6 +1567,23 @@ static void do_exec (int child_err_report_fd, char **argv) { +#ifdef DBUS_BUILD_TESTS + int i, max_open; + + max_open = sysconf (_SC_OPEN_MAX); + + + for (i = 3; i < max_open; i++) + { + int retval; + + retval = fcntl (i, F_GETFD); + + if (retval != -1 && !(retval & FD_CLOEXEC)) + _dbus_warn ("Fd %d did not have the close-on-exec flag set!\n", i); + } +#endif + execvp (argv[0], argv); /* Exec failed */ @@ -1577,19 +1598,13 @@ _dbus_spawn_async (char **argv, { int pid = -1, grandchild_pid; int child_err_report_pipe[2] = { -1, -1 }; - int child_pid_report_pipe[2] = { -1, -1 }; int status; - printf ("spawning application: %s\n", argv[0]); - if (!make_pipe (child_err_report_pipe, error)) return FALSE; - if (!make_pipe (child_pid_report_pipe, error)) - goto cleanup_and_fail; - pid = fork (); - + if (pid < 0) { dbus_set_error (error, @@ -1612,7 +1627,6 @@ _dbus_spawn_async (char **argv, * though */ close_and_invalidate (&child_err_report_pipe[0]); - close_and_invalidate (&child_pid_report_pipe[0]); /* We need to fork an intermediate child that launches the * final child. The purpose of the intermediate child @@ -1623,10 +1637,6 @@ _dbus_spawn_async (char **argv, if (grandchild_pid < 0) { - /* report -1 as child PID */ - write (child_pid_report_pipe[1], &grandchild_pid, - sizeof(grandchild_pid)); - write_err_and_exit (child_err_report_pipe[1], CHILD_FORK_FAILED); } @@ -1637,9 +1647,6 @@ _dbus_spawn_async (char **argv, } else { - write (child_pid_report_pipe[1], &grandchild_pid, sizeof(grandchild_pid)); - close_and_invalidate (&child_pid_report_pipe[1]); - _exit (0); } } @@ -1652,7 +1659,6 @@ _dbus_spawn_async (char **argv, /* Close the uncared-about ends of the pipes */ close_and_invalidate (&child_err_report_pipe[1]); - close_and_invalidate (&child_pid_report_pipe[1]); wait_again: if (waitpid (pid, &status, 0) < 0) @@ -1716,8 +1722,6 @@ _dbus_spawn_async (char **argv, close_and_invalidate (&child_err_report_pipe[0]); close_and_invalidate (&child_err_report_pipe[1]); - close_and_invalidate (&child_pid_report_pipe[0]); - close_and_invalidate (&child_pid_report_pipe[1]); return FALSE; } @@ -1731,4 +1735,19 @@ _dbus_disable_sigpipe (void) signal (SIGPIPE, SIG_IGN); } +void +_dbus_fd_set_close_on_exec (int fd) +{ + int val; + + val = fcntl (fd, F_GETFD, 0); + + if (val < 0) + return; + + val |= FD_CLOEXEC; + + fcntl (fd, F_SETFD, val); +} + /** @} end of sysdeps */ diff --git a/dbus/dbus-transport-unix.c b/dbus/dbus-transport-unix.c index ef50863d..84703345 100644 --- a/dbus/dbus-transport-unix.c +++ b/dbus/dbus-transport-unix.c @@ -1102,6 +1102,8 @@ _dbus_transport_new_for_domain_socket (const char *path, if (fd < 0) return NULL; + _dbus_fd_set_close_on_exec (fd); + _dbus_verbose ("Successfully connected to unix socket %s\n", path); -- cgit