bus: make use of new unix fd limits
authorLennart Poettering <lennart@poettering.net>
Tue, 19 May 2009 23:33:17 +0000 (01:33 +0200)
committerLennart Poettering <lennart@poettering.net>
Wed, 20 May 2009 00:10:17 +0000 (02:10 +0200)
Create configuration settings and enforce message unix fd limits the
same way we do for allocated message memory.

bus/bus.c
bus/bus.h
bus/config-parser.c
bus/dbus-daemon.1.in
bus/session.conf.in

index 1412ea2..129b2e6 100644 (file)
--- a/bus/bus.c
+++ b/bus/bus.c
@@ -190,6 +190,12 @@ new_connection_callback (DBusServer     *server,
 
   dbus_connection_set_max_message_size (new_connection,
                                         context->limits.max_message_size);
+
+  dbus_connection_set_max_received_unix_fds (new_connection,
+                                         context->limits.max_incoming_unix_fds);
+
+  dbus_connection_set_max_message_unix_fds (new_connection,
+                                        context->limits.max_message_unix_fds);
   
   dbus_connection_set_allow_anonymous (new_connection,
                                        context->allow_anonymous);
@@ -1471,8 +1477,8 @@ bus_context_check_security_policy (BusContext     *context,
 
   /* See if limits on size have been exceeded */
   if (proposed_recipient &&
-      dbus_connection_get_outgoing_size (proposed_recipient) >
-      context->limits.max_outgoing_bytes)
+      ((dbus_connection_get_outgoing_size (proposed_recipient) > context->limits.max_outgoing_bytes) ||
+       (dbus_connection_get_outgoing_unix_fds (proposed_recipient) > context->limits.max_outgoing_unix_fds)))
     {
       dbus_set_error (error, DBUS_ERROR_LIMITS_EXCEEDED,
                       "The destination service \"%s\" has a full message queue",
index 74bdb82..aba1704 100644 (file)
--- a/bus/bus.h
+++ b/bus/bus.h
@@ -47,8 +47,11 @@ typedef struct BusMatchRule     BusMatchRule;
 typedef struct
 {
   long max_incoming_bytes;          /**< How many incoming message bytes for a single connection */
+  long max_incoming_unix_fds;       /**< How many incoming message unix fds for a single connection */
   long max_outgoing_bytes;          /**< How many outgoing bytes can be queued for a single connection */
+  long max_outgoing_unix_fds;       /**< How many outgoing unix fds can be queued for a single connection */
   long max_message_size;            /**< Max size of a single message in bytes */
+  long max_message_unix_fds;        /**< Max number of unix fds of a single message*/
   int activation_timeout;           /**< How long to wait for an activation to time out */
   int auth_timeout;                 /**< How long to wait for an authentication to time out */
   int max_completed_connections;    /**< Max number of authorized connections */
index c3e8fba..784c831 100644 (file)
@@ -404,6 +404,15 @@ bus_config_parser_new (const DBusString      *basedir,
       parser->limits.max_incoming_bytes = _DBUS_ONE_MEGABYTE * 127;
       parser->limits.max_outgoing_bytes = _DBUS_ONE_MEGABYTE * 127;
       parser->limits.max_message_size = _DBUS_ONE_MEGABYTE * 32;
+
+      /* We set relatively conservative values here since due to the
+      way SCM_RIGHTS works we need to preallocate an array for the
+      maximum number of file descriptors we can receive. Picking a
+      high value here thus translates directly to more memory
+      allocation. */
+      parser->limits.max_incoming_unix_fds = 1024*4;
+      parser->limits.max_outgoing_unix_fds = 1024*4;
+      parser->limits.max_message_unix_fds = 1024;
       
       /* Making this long means the user has to wait longer for an error
        * message if something screws up, but making it too short means
@@ -1828,16 +1837,31 @@ set_limit (BusConfigParser *parser,
       must_be_positive = TRUE;
       parser->limits.max_incoming_bytes = value;
     }
+  else if (strcmp (name, "max_incoming_unix_fds") == 0)
+    {
+      must_be_positive = TRUE;
+      parser->limits.max_incoming_unix_fds = value;
+    }
   else if (strcmp (name, "max_outgoing_bytes") == 0)
     {
       must_be_positive = TRUE;
       parser->limits.max_outgoing_bytes = value;
     }
+  else if (strcmp (name, "max_outgoing_unix_fds") == 0)
+    {
+      must_be_positive = TRUE;
+      parser->limits.max_outgoing_unix_fds = value;
+    }
   else if (strcmp (name, "max_message_size") == 0)
     {
       must_be_positive = TRUE;
       parser->limits.max_message_size = value;
     }
+  else if (strcmp (name, "max_message_unix_fds") == 0)
+    {
+      must_be_positive = TRUE;
+      parser->limits.max_message_unix_fds = value;
+    }
   else if (strcmp (name, "service_start_timeout") == 0)
     {
       must_be_positive = TRUE;
@@ -2979,8 +3003,11 @@ limits_equal (const BusLimits *a,
 {
   return
     (a->max_incoming_bytes == b->max_incoming_bytes
+     || a->max_incoming_unix_fds == b->max_incoming_unix_fds
      || a->max_outgoing_bytes == b->max_outgoing_bytes
+     || a->max_outgoing_unix_fds == b->max_outgoing_unix_fds
      || a->max_message_size == b->max_message_size
+     || a->max_message_unix_fds == b->max_message_unix_fds
      || a->activation_timeout == b->activation_timeout
      || a->auth_timeout == b->auth_timeout
      || a->max_completed_connections == b->max_completed_connections
index 4b55ac2..8d51813 100644 (file)
@@ -365,10 +365,15 @@ Available limit names are:
 .nf
       "max_incoming_bytes"         : total size in bytes of messages
                                      incoming from a single connection
+      "max_incoming_unix_fds"      : total number of unix fds of messages
+                                     incoming from a single connection
       "max_outgoing_bytes"         : total size in bytes of messages
                                      queued up for a single connection
+      "max_outgoing_unix_fds"      : total number of unix fds of messages
+                                     queued up for a single connection
       "max_message_size"           : max size of a single message in
                                      bytes
+      "max_message_unix_fds"       : max unix fds of a single message
       "service_start_timeout"      : milliseconds (thousandths) until 
                                      a started service has to connect
       "auth_timeout"               : milliseconds (thousandths) a
index 794eb8d..aed320e 100644 (file)
 
   <!-- the memory limits are 1G instead of say 4G because they can't exceed 32-bit signed int max -->
   <limit name="max_incoming_bytes">1000000000</limit>
+  <limit name="max_incoming_unix_fds">250000000</limit>
   <limit name="max_outgoing_bytes">1000000000</limit>
+  <limit name="max_outgoing_unix_fds">250000000</limit>
   <limit name="max_message_size">1000000000</limit>
+  <limit name="max_message_unix_fds">4096</limit>
   <limit name="service_start_timeout">120000</limit>  
   <limit name="auth_timeout">240000</limit>
   <limit name="max_completed_connections">100000</limit>