]> git.ipfire.org Git - thirdparty/dbus.git/commitdiff
2007-07-24 Havoc Pennington <hp@redhat.com>
authorHavoc Pennington <hp@redhat.com>
Tue, 24 Jul 2007 22:11:00 +0000 (22:11 +0000)
committerHavoc Pennington <hp@redhat.com>
Tue, 24 Jul 2007 22:11:00 +0000 (22:11 +0000)
* configure.in: add AM_PROG_CC_C_O to allow per-target CPPFLAGS

* bus/dispatch.c (bus_dispatch_test_conf): Fix up setting
TEST_LAUNCH_HELPER_CONFIG to include the full path, and enable
test shell_fail_service_auto_start when use_launcher==TRUE

* bus/activation-helper-bin.c (convert_error_to_exit_code): pass
through the INVALID_ARGS error so the test suite works

* bus/activation.c (handle_activation_exit_error): return
DBUS_ERROR_NO_MEMORY if we get BUS_SPAWN_EXIT_CODE_NO_MEMORY

* dbus/dbus-spawn.c (_dbus_babysitter_get_child_exit_status):
return only the exit code of the child, not the entire thingy from
waitpid(), and make the return value indicate whether the child
exited normally (with a status code)

* bus/bus.c (process_config_first_time_only): _dbus_strdup works
on NULL so no need to check
(process_config_every_time): move servicehelper init here, so we
reload it on HUP or config file change

* bus/Makefile.am (install-data-hook): remove comment because
Emacs make mode seems to be grumpy about it

ChangeLog
bus/Makefile.am
bus/activation-exit-codes.h
bus/activation-helper-bin.c
bus/activation.c
bus/bus.c
bus/config-parser.c
bus/dispatch.c
configure.in
dbus/dbus-spawn.c

index f580a32f2f0c22d183e47f5ee1db42ae3f97d5ae..3f7918ef267dbcbd22250925d7284eb1b862d171 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,30 @@
+2007-07-24  Havoc Pennington  <hp@redhat.com>
+
+       * configure.in: add AM_PROG_CC_C_O to allow per-target CPPFLAGS
+
+       * bus/dispatch.c (bus_dispatch_test_conf): Fix up setting
+       TEST_LAUNCH_HELPER_CONFIG to include the full path, and enable
+       test shell_fail_service_auto_start when use_launcher==TRUE
+
+       * bus/activation-helper-bin.c (convert_error_to_exit_code): pass
+       through the INVALID_ARGS error so the test suite works
+
+       * bus/activation.c (handle_activation_exit_error): return
+       DBUS_ERROR_NO_MEMORY if we get BUS_SPAWN_EXIT_CODE_NO_MEMORY
+
+       * dbus/dbus-spawn.c (_dbus_babysitter_get_child_exit_status):
+       return only the exit code of the child, not the entire thingy from 
+       waitpid(), and make the return value indicate whether the child 
+       exited normally (with a status code)
+
+       * bus/bus.c (process_config_first_time_only): _dbus_strdup works
+       on NULL so no need to check
+       (process_config_every_time): move servicehelper init here, so we
+       reload it on HUP or config file change
+
+       * bus/Makefile.am (install-data-hook): remove comment because
+       Emacs make mode seems to be grumpy about it
+
 2007-07-24  Richard Hughes  <richard@hughsie.com>
 
        * bus/Makefile.am:
index d4eae307261e4d2f9212eb91fb391af609934a5c..d521fa7b3585c12b83fa2959561cbdc3c9353546 100644 (file)
@@ -188,7 +188,6 @@ install-data-hook:
        $(mkinstalldirs) $(DESTDIR)$(datadir)/dbus-1/system-services
        $(mkinstalldirs) $(DESTDIR)$(libexecdir)/dbus-1
        $(INSTALL_PROGRAM) dbus-daemon-launch-helper $(DESTDIR)$(libexecdir)
-       ## This is SETUID! <insert suitable warning here...>
        if test `id -u` -eq 0; then \
                chown root:$(DBUS_USER) $(DESTDIR)$(libexecdir)/dbus-daemon-launch-helper; \
                chmod 4750 $(DESTDIR)$(libexecdir)/dbus-daemon-launch-helper; \
index 0e858f14d7df53afe9cd5b8f7b81a4c1b4fa687c..86a005ce5c7133df12747de48dcf0cdfeb5a82dc 100644 (file)
@@ -34,5 +34,6 @@
 #define BUS_SPAWN_EXIT_CODE_PERMISSIONS_INVALID  6
 #define BUS_SPAWN_EXIT_CODE_FILE_INVALID         7
 #define BUS_SPAWN_EXIT_CODE_EXEC_FAILED          8
+#define BUS_SPAWN_EXIT_CODE_INVALID_ARGS         9
 
 #endif /* BUS_ACTIVATION_EXIT_CODES_H */
index 6b9ec1f5809f63620a684c6a2401ac0f2232866b..248a86f77b2207af487cdbab2a44c3cb23cfa195 100644 (file)
@@ -56,7 +56,12 @@ convert_error_to_exit_code (DBusError *error)
   if (dbus_error_has_name (error, DBUS_ERROR_SPAWN_EXEC_FAILED))
     return BUS_SPAWN_EXIT_CODE_EXEC_FAILED;
 
+  if (dbus_error_has_name (error, DBUS_ERROR_INVALID_ARGS))
+    return BUS_SPAWN_EXIT_CODE_INVALID_ARGS;
+  
   /* should we assert? */
+  fprintf(stderr, "%s: %s\n", error->name, error->message);
+  
   return BUS_SPAWN_EXIT_CODE_SETUP_FAILED;
 }
 
index c49bc8818e56b4fa0ede0307b847e4a8ab5e3781..d5162ec2adb68c2151371c21eb2473503b9c0266 100644 (file)
@@ -1122,13 +1122,14 @@ pending_activation_failed (BusPendingActivation *pending_activation,
  * Depending on the exit code of the helper, set the error accordingly
  */
 static void
-handle_activation_exit_error (int exit_code, DBusError *error)
+handle_activation_exit_error (int        exit_code,
+                              DBusError *error)
 {
   switch (exit_code)
     {
     case BUS_SPAWN_EXIT_CODE_NO_MEMORY:
-      dbus_set_error (error, DBUS_ERROR_SPAWN_SETUP_FAILED,
-                      "Launcher could not run as out of memory");
+      dbus_set_error (error, DBUS_ERROR_NO_MEMORY,
+                      "Launcher could not run (out of memory)");
       break;
     case BUS_SPAWN_EXIT_CODE_SETUP_FAILED:
       dbus_set_error (error, DBUS_ERROR_SPAWN_SETUP_FAILED,
@@ -1154,6 +1155,10 @@ handle_activation_exit_error (int exit_code, DBusError *error)
       dbus_set_error (error, DBUS_ERROR_SPAWN_EXEC_FAILED,
                       "Cannot launch daemon, file not found or permissions invalid");
       break;
+    case BUS_SPAWN_EXIT_CODE_INVALID_ARGS:
+      dbus_set_error (error, DBUS_ERROR_INVALID_ARGS,
+                      "Invalid arguments to command line");
+      break;
     default:
       dbus_set_error (error, DBUS_ERROR_SPAWN_CHILD_EXITED,
                       "Launch helper exited with unknown return code %i", exit_code);
index 627e49d304e4665300f38f95f9c258cc7a078554..21e8037ec0508e92ab6ceb24f647730804837256 100644 (file)
--- a/bus/bus.c
+++ b/bus/bus.c
@@ -254,8 +254,9 @@ setup_server (BusContext *context,
 }
 
 /* This code only gets executed the first time the
-   config files are parsed.  It is not executed
-   when config files are reloaded.*/
+ * config files are parsed.  It is not executed
+ * when config files are reloaded.
+ */
 static dbus_bool_t
 process_config_first_time_only (BusContext      *context,
                                BusConfigParser *parser,
@@ -263,7 +264,7 @@ process_config_first_time_only (BusContext      *context,
 {
   DBusList *link;
   DBusList **addresses;
-  const char *user, *pidfile, *servicehelper;
+  const char *user, *pidfile;
   char **auth_mechanisms;
   DBusList **auth_mechanisms_list;
   int len;
@@ -299,11 +300,6 @@ process_config_first_time_only (BusContext      *context,
   /* keep around the pid filename so we can delete it later */
   context->pidfile = _dbus_strdup (pidfile);
 
-  /* we need to configure this so we can test the service helper */
-  servicehelper = bus_config_parser_get_servicehelper (parser);
-  if (servicehelper != NULL)
-    context->servicehelper = _dbus_strdup (servicehelper);
-
   /* Build an array of auth mechanisms */
   
   auth_mechanisms_list = bus_config_parser_get_mechanisms (parser);
@@ -398,8 +394,11 @@ process_config_first_time_only (BusContext      *context,
 }
 
 /* This code gets executed every time the config files
-   are parsed: both during BusContext construction
-   and on reloads. */
+ * are parsed: both during BusContext construction
+ * and on reloads. This function is slightly screwy
+ * since it can do a "half reload" in out-of-memory
+ * situations. Realistically, unlikely to ever matter.
+ */
 static dbus_bool_t
 process_config_every_time (BusContext      *context,
                           BusConfigParser *parser,
@@ -411,7 +410,9 @@ process_config_every_time (BusContext      *context,
   DBusList **dirs;
   BusActivation *new_activation;
   char *addr;
-
+  const char *servicehelper;
+  char *s;
+  
   dbus_bool_t retval;
 
   _DBUS_ASSERT_ERROR_IS_CLEAR (error);
@@ -477,6 +478,21 @@ process_config_every_time (BusContext      *context,
   /* get the service directories */
   dirs = bus_config_parser_get_service_dirs (parser);
 
+  /* and the service helper */
+  servicehelper = bus_config_parser_get_servicehelper (parser);
+
+  s = _dbus_strdup(servicehelper);
+  if (s == NULL && servicehelper != NULL)
+    {
+      BUS_SET_OOM (error);
+      goto failed;
+    }
+  else
+    {
+      dbus_free(context->servicehelper);
+      context->servicehelper = s;
+    }
+  
   /* Create activation subsystem */
   new_activation = bus_activation_new (context, &full_address,
                                        dirs, error);
index 43e516e32df7c1b0726fa3284826d106a0ce8d06..d6df4abb44422b98519d00cdf79e924778399e84 100644 (file)
@@ -2073,15 +2073,8 @@ servicehelper_path (BusConfigParser   *parser,
 {
   const char *filename_str;
   char *servicehelper;
-  filename_str = _dbus_string_get_const_data (filename);
 
-  /* check if helper exists... */
-  if (!_dbus_file_exists (filename_str))
-    {
-      dbus_set_error (error, DBUS_ERROR_FILE_NOT_FOUND,
-                      "setuid helper '%s'not found", filename_str);
-      return FALSE;
-    }
+  filename_str = _dbus_string_get_const_data (filename);
 
   /* copy to avoid overwriting with NULL on OOM */
   servicehelper = _dbus_strdup (filename_str);
@@ -2097,6 +2090,13 @@ servicehelper_path (BusConfigParser   *parser,
   dbus_free (parser->servicehelper);
   parser->servicehelper = servicehelper;
 
+  /* We don't check whether the helper exists; instead we
+   * would just fail to ever activate anything if it doesn't.
+   * This allows an admin to fix the problem if it doesn't exist.
+   * It also allows the parser test suite to successfully parse
+   * test cases without installing the helper. ;-)
+   */
+  
   return TRUE;
 }
 
index b020bb0bd9a28b259efb129e4c06dd5ac6be56d9..d434e808a1829b6ddf6cad9ce689f5cb23f703e8 100644 (file)
@@ -4407,6 +4407,40 @@ check2_try_iterations (BusContext     *context,
     }
 }
 
+static dbus_bool_t
+setenv_TEST_LAUNCH_HELPER_CONFIG(const DBusString *test_data_dir,
+                                 const char       *filename)
+{
+  DBusString full;
+  DBusString file;
+
+  if (!_dbus_string_init (&full))
+    return FALSE;
+
+  if (!_dbus_string_copy (test_data_dir, 0, &full, 0))
+    {
+      _dbus_string_free (&full);
+      return FALSE;
+    }      
+
+  _dbus_string_init_const (&file, filename);
+  
+  if (!_dbus_concat_dir_and_file (&full, &file))
+    {
+      _dbus_string_free (&full);
+      return FALSE;
+    }
+
+  _dbus_verbose ("Setting TEST_LAUNCH_HELPER_CONFIG to '%s'\n", 
+                 _dbus_string_get_const_data (&full));
+  
+  _dbus_setenv ("TEST_LAUNCH_HELPER_CONFIG", _dbus_string_get_const_data (&full));
+
+  _dbus_string_free (&full);
+
+  return TRUE;
+}
+
 static dbus_bool_t
 bus_dispatch_test_conf (const DBusString *test_data_dir,
                        const char       *filename,
@@ -4419,7 +4453,8 @@ bus_dispatch_test_conf (const DBusString *test_data_dir,
   DBusError error;
 
   /* save the config name for the activation helper */
-  _dbus_setenv ("TEST_LAUNCH_HELPER_CONFIG", filename);
+  if (!setenv_TEST_LAUNCH_HELPER_CONFIG (test_data_dir, filename))
+    _dbus_assert_not_reached ("no memory setting TEST_LAUNCH_HELPER_CONFIG");
 
   dbus_error_init (&error);
   
@@ -4524,9 +4559,8 @@ bus_dispatch_test_conf (const DBusString *test_data_dir,
 #endif
 
   /* only do the shell fail test if we are not using the launcher */
-  if (!use_launcher)
-    check2_try_iterations (context, foo, "shell_fail_service_auto_start",
-                           check_shell_fail_service_auto_start);
+  check2_try_iterations (context, foo, "shell_fail_service_auto_start",
+                         check_shell_fail_service_auto_start);
 
   /* specific to launcher */
   if (use_launcher)
@@ -4572,8 +4606,9 @@ bus_dispatch_test_conf_fail (const DBusString *test_data_dir,
   DBusError error;
 
   /* save the config name for the activation helper */
-  _dbus_setenv ("TEST_LAUNCH_HELPER_CONFIG", filename);
-
+  if (!setenv_TEST_LAUNCH_HELPER_CONFIG (test_data_dir, filename))
+    _dbus_assert_not_reached ("no memory setting TEST_LAUNCH_HELPER_CONFIG");
+  
   dbus_error_init (&error);
   
   context = bus_context_new_test (test_data_dir, filename);
index d999f43b5dab1ebc91d6bc92231f8fd0e8f186b6..7b7cf262f1e8555967d14487e2cdcd600dcb364b 100644 (file)
@@ -41,6 +41,7 @@ AC_SUBST(LT_AGE)
 
 
 AC_PROG_CC
+AM_PROG_CC_C_O
 AC_PROG_CXX
 AC_ISC_POSIX
 AC_HEADER_STDC
index 125aea7c3b3357f153244f13c2cf85508ca5caa6..810536fd821248d854d6eb8543cb5eea9c4bd504 100644 (file)
@@ -417,7 +417,7 @@ read_data (DBusBabysitter *sitter,
                   {
                     sitter->have_child_status = TRUE;
                     sitter->status = arg;
-                    sitter->errnum = WEXITSTATUS (sitter->status);
+                    sitter->errnum = 0;
                     _dbus_verbose ("recorded child status exited = %d signaled = %d exitstatus = %d termsig = %d\n",
                                    WIFEXITED (sitter->status), WIFSIGNALED (sitter->status),
                                    WEXITSTATUS (sitter->status), WTERMSIG (sitter->status));
@@ -624,26 +624,29 @@ _dbus_babysitter_get_child_exited (DBusBabysitter *sitter)
 }
 
 /**
- * Gets the exit status of the child. We do this so implimentation specific
- * detail is not cluttering up dbus, for example the system laucher code.
+ * Gets the exit status of the child. We do this so implementation specific
+ * detail is not cluttering up dbus, for example the system launcher code.
+ * This can only be called if the child has exited, i.e. call
+ * _dbus_babysitter_get_child_exited(). It returns FALSE if the child
+ * did not return a status code, e.g. because the child was signaled
+ * or we failed to ever launch the child in the first place.
  *
  * @param sitter the babysitter
  * @param status the returned status code
  * @returns #FALSE on failure
  */
 dbus_bool_t
-_dbus_babysitter_get_child_exit_status (DBusBabysitter *sitter, int *status)
+_dbus_babysitter_get_child_exit_status (DBusBabysitter *sitter,
+                                        int            *status)
 {
   if (!_dbus_babysitter_get_child_exited (sitter))
     _dbus_assert_not_reached ("Child has not exited");
+  
+  if (!sitter->have_child_status ||
+      !(WIFEXITED (sitter->status)))
+    return FALSE;
 
-  if (sitter->errnum != WEXITSTATUS (sitter->status))
-    _dbus_assert_not_reached ("Status is not exit!");
-
-  if (!sitter->have_child_status)
-    _dbus_assert_not_reached ("Not a child!");
-
-  *status = sitter->status;
+  *status = WEXITSTATUS (sitter->status);
   return TRUE;
 }