diff options
| author | Havoc Pennington <hp@redhat.com> | 2005-02-25 22:03:30 +0000 | 
|---|---|---|
| committer | Havoc Pennington <hp@redhat.com> | 2005-02-25 22:03:30 +0000 | 
| commit | 7ce7502e1ae23766ba40105327de787c2d1cef9d (patch) | |
| tree | 06fcb80d134ca45a88a510e0f53d34e2f415fd50 | |
| parent | 1b5dace8e6986965af7b573b3b2c5991af11cf6e (diff) | |
2005-02-25  Havoc Pennington  <hp@redhat.com>
	* doc/dbus-specification.xml: document the GUID thing
	* dbus/dbus-server.c (_dbus_server_init_base): initialize a
	globally unique ID for the server, and put a "guid=hexencoded"
	field in the address
	* dbus/dbus-bus.c: fix missing #include of dbus-threads-internal.h
	* dbus/dbus-message.c: ditto
	* dbus/dbus-dataslot.c: ditto
	* dbus/dbus-list.c: ditto
	* dbus/dbus-internals.h: wait, just include
	dbus-threads-internal.h here
	* dbus/dbus-string.c (_dbus_string_copy_to_buffer): move back for
	use in main library
	* dbus/dbus-sysdeps.c (_dbus_generate_random_bytes_buffer): new function
| -rw-r--r-- | ChangeLog | 24 | ||||
| -rw-r--r-- | dbus/dbus-bus.c | 1 | ||||
| -rw-r--r-- | dbus/dbus-dataslot.c | 2 | ||||
| -rw-r--r-- | dbus/dbus-internals.h | 2 | ||||
| -rw-r--r-- | dbus/dbus-list.c | 2 | ||||
| -rw-r--r-- | dbus/dbus-message.c | 1 | ||||
| -rw-r--r-- | dbus/dbus-server-protected.h | 13 | ||||
| -rw-r--r-- | dbus/dbus-server.c | 68 | ||||
| -rw-r--r-- | dbus/dbus-string-util.c | 24 | ||||
| -rw-r--r-- | dbus/dbus-string.c | 24 | ||||
| -rw-r--r-- | dbus/dbus-sysdeps.c | 59 | ||||
| -rw-r--r-- | dbus/dbus-sysdeps.h | 10 | ||||
| -rw-r--r-- | doc/dbus-specification.xml | 22 | 
13 files changed, 204 insertions, 48 deletions
@@ -1,3 +1,27 @@ +2005-02-25  Havoc Pennington  <hp@redhat.com> + +	* doc/dbus-specification.xml: document the GUID thing + +	* dbus/dbus-server.c (_dbus_server_init_base): initialize a +	globally unique ID for the server, and put a "guid=hexencoded" +	field in the address + +	* dbus/dbus-bus.c: fix missing #include of dbus-threads-internal.h + +	* dbus/dbus-message.c: ditto + +	* dbus/dbus-dataslot.c: ditto + +	* dbus/dbus-list.c: ditto + +	* dbus/dbus-internals.h: wait, just include +	dbus-threads-internal.h here +	 +	* dbus/dbus-string.c (_dbus_string_copy_to_buffer): move back for +	use in main library + +	* dbus/dbus-sysdeps.c (_dbus_generate_random_bytes_buffer): new function +  2005-02-24  Colin Walters  <walters@verbum.org>  	* test/glib/Makefile.am (EXTRA_DIST): Add test-service-glib.xml diff --git a/dbus/dbus-bus.c b/dbus/dbus-bus.c index 188418c2..fedee0f0 100644 --- a/dbus/dbus-bus.c +++ b/dbus/dbus-bus.c @@ -27,6 +27,7 @@  #include "dbus-internals.h"  #include "dbus-message.h"  #include "dbus-marshal-validate.h" +#include "dbus-threads-internal.h"  #include <string.h>  /** diff --git a/dbus/dbus-dataslot.c b/dbus/dbus-dataslot.c index 8026d048..8a2937de 100644 --- a/dbus/dbus-dataslot.c +++ b/dbus/dbus-dataslot.c @@ -21,7 +21,7 @@   *   */  #include "dbus-dataslot.h" -#include "dbus-threads.h" +#include "dbus-threads-internal.h"  /**   * @defgroup DBusDataSlot Data slots diff --git a/dbus/dbus-internals.h b/dbus/dbus-internals.h index dcbc6183..b141c23d 100644 --- a/dbus/dbus-internals.h +++ b/dbus/dbus-internals.h @@ -33,7 +33,7 @@  #include <dbus/dbus-types.h>  #include <dbus/dbus-errors.h>  #include <dbus/dbus-sysdeps.h> -#include <dbus/dbus-threads.h> +#include <dbus/dbus-threads-internal.h>  DBUS_BEGIN_DECLS diff --git a/dbus/dbus-list.c b/dbus/dbus-list.c index 949e70a8..7389c268 100644 --- a/dbus/dbus-list.c +++ b/dbus/dbus-list.c @@ -24,7 +24,7 @@  #include "dbus-internals.h"  #include "dbus-list.h"  #include "dbus-mempool.h" -#include "dbus-threads.h" +#include "dbus-threads-internal.h"  /**   * @defgroup DBusList Linked list diff --git a/dbus/dbus-message.c b/dbus/dbus-message.c index 7ff5762c..672a72b4 100644 --- a/dbus/dbus-message.c +++ b/dbus/dbus-message.c @@ -32,6 +32,7 @@  #include "dbus-object-tree.h"  #include "dbus-memory.h"  #include "dbus-list.h" +#include "dbus-threads-internal.h"  #include <string.h>  /** diff --git a/dbus/dbus-server-protected.h b/dbus/dbus-server-protected.h index 284d02c5..dbbc3c62 100644 --- a/dbus/dbus-server-protected.h +++ b/dbus/dbus-server-protected.h @@ -35,6 +35,16 @@  DBUS_BEGIN_DECLS  typedef struct DBusServerVTable DBusServerVTable; +typedef union DBusGUID DBusGUID; + +/** + * A server's globally unique ID + */ +union DBusGUID +{ +  dbus_uint32_t as_uint32s[4]; +  unsigned char as_bytes[16]; +};  /**   * Virtual table to be implemented by all server "subclasses" @@ -56,6 +66,9 @@ struct DBusServer    DBusAtomic refcount;                        /**< Reference count. */    const DBusServerVTable *vtable;             /**< Virtual methods for this instance. */    DBusMutex *mutex;                           /**< Lock on the server object */ + +  DBusGUID guid;                              /**< Globally unique ID of server */  +      DBusWatchList *watches;                     /**< Our watches */    DBusTimeoutList *timeouts;                  /**< Our timeouts */   diff --git a/dbus/dbus-server.c b/dbus/dbus-server.c index 156d5ccd..20fb5f3c 100644 --- a/dbus/dbus-server.c +++ b/dbus/dbus-server.c @@ -52,6 +52,58 @@   * @{   */ +static void +init_guid (DBusGUID *guid) +{ +  long now; +  char *p; +  int ts_size; + +  _dbus_get_current_time (&now, NULL); + +  guid->as_uint32s[0] = now; + +  ts_size = sizeof (guid->as_uint32s[0]); +  p = ((char*)guid->as_bytes) + ts_size; +   +  _dbus_generate_random_bytes_buffer (p, +                                      sizeof (guid->as_bytes) - ts_size); +} + +/* this is a little fragile since it assumes the address doesn't + * already have a guid, but it shouldn't + */ +static char* +copy_address_with_guid_appended (const DBusString *address, +                                 const DBusGUID   *guid) +{ +  DBusString with_guid; +  DBusString guid_str; +  char *retval; +   +  if (!_dbus_string_init (&with_guid)) +    return NULL; + +  _dbus_string_init_const_len (&guid_str, guid->as_bytes, +                               sizeof (guid->as_bytes)); + +  if (!_dbus_string_copy (address, 0, &with_guid, 0) || +      !_dbus_string_append (&with_guid, ",guid=") || +      !_dbus_string_hex_encode (&guid_str, 0, +                                &with_guid, _dbus_string_get_length (&with_guid))) +    { +      _dbus_string_free (&with_guid); +      return NULL; +    } + +  retval = NULL; +  _dbus_string_copy_data (&with_guid, &retval); + +  _dbus_string_free (&with_guid); +       +  return retval; /* may be NULL if copy failed */ +} +  /**   * Initializes the members of the DBusServer base class.   * Chained up to by subclass constructors. @@ -65,17 +117,21 @@ dbus_bool_t  _dbus_server_init_base (DBusServer             *server,                          const DBusServerVTable *vtable,                          const DBusString       *address) -{ +{      server->vtable = vtable;    server->refcount.value = 1;    server->address = NULL;    server->watches = NULL;    server->timeouts = NULL; -   -  if (!_dbus_string_copy_data (address, &server->address)) -    goto failed; +  init_guid (&server->guid); + +  server->address = copy_address_with_guid_appended (address, +                                                     &server->guid); +  if (server->address == NULL) +    goto failed; +      server->mutex = _dbus_mutex_new ();    if (server->mutex == NULL)      goto failed; @@ -438,7 +494,9 @@ dbus_server_listen (const char     *address,    for (i = 0; i < len; i++)      { -      const char *method = dbus_address_entry_get_method (entries[i]); +      const char *method; + +      method = dbus_address_entry_get_method (entries[i]);        if (strcmp (method, "unix") == 0)  	{ diff --git a/dbus/dbus-string-util.c b/dbus/dbus-string-util.c index 0610c66d..ddb9d750 100644 --- a/dbus/dbus-string-util.c +++ b/dbus/dbus-string-util.c @@ -32,30 +32,6 @@   */  /** - * Copies the contents of a DBusString into a different - * buffer. The resulting buffer will be nul-terminated. - *  - * @param str a string - * @param buffer a C buffer to copy data to - * @param avail_len maximum length of C buffer - */ -void -_dbus_string_copy_to_buffer (const DBusString  *str, -			     char              *buffer, -			     int                avail_len) -{ -  int copy_len; -  DBUS_CONST_STRING_PREAMBLE (str); - -  _dbus_assert (avail_len >= 0); - -  copy_len = MIN (avail_len, real->len+1); -  memcpy (buffer, real->str, copy_len); -  if (avail_len > 0 && avail_len == copy_len) -    buffer[avail_len-1] = '\0'; -} - -/**   * Returns whether a string ends with the given suffix   *   * @todo memcmp might make this faster. diff --git a/dbus/dbus-string.c b/dbus/dbus-string.c index 5088bca9..86d3eb83 100644 --- a/dbus/dbus-string.c +++ b/dbus/dbus-string.c @@ -708,6 +708,30 @@ _dbus_string_copy_data (const DBusString  *str,    return TRUE;  } +/** + * Copies the contents of a DBusString into a different + * buffer. The resulting buffer will be nul-terminated. + *  + * @param str a string + * @param buffer a C buffer to copy data to + * @param avail_len maximum length of C buffer + */ +void +_dbus_string_copy_to_buffer (const DBusString  *str, +			     char              *buffer, +			     int                avail_len) +{ +  int copy_len; +  DBUS_CONST_STRING_PREAMBLE (str); + +  _dbus_assert (avail_len >= 0); + +  copy_len = MIN (avail_len, real->len+1); +  memcpy (buffer, real->str, copy_len); +  if (avail_len > 0 && avail_len == copy_len) +    buffer[avail_len-1] = '\0'; +} +  #ifdef DBUS_BUILD_TESTS  /**   * Copies a segment of the string into a char* diff --git a/dbus/dbus-sysdeps.c b/dbus/dbus-sysdeps.c index 83c1ce4c..830e26f1 100644 --- a/dbus/dbus-sysdeps.c +++ b/dbus/dbus-sysdeps.c @@ -2328,15 +2328,12 @@ _dbus_concat_dir_and_file (DBusString       *dir,  }  static dbus_bool_t -pseudorandom_generate_random_bytes (DBusString *str, -                                    int         n_bytes) +pseudorandom_generate_random_bytes_buffer (char *buffer, +                                           int   n_bytes)  { -  int old_len;    unsigned long tv_usec;    int i; -  old_len = _dbus_string_get_length (str); -    /* fall back to pseudorandom */    _dbus_verbose ("Falling back to pseudorandom for %d bytes\n",                   n_bytes); @@ -2352,18 +2349,56 @@ pseudorandom_generate_random_bytes (DBusString *str,        r = rand ();        b = (r / (double) RAND_MAX) * 255.0; -           -      if (!_dbus_string_append_byte (str, b)) -        goto failed; -           + +      buffer[i] = b; +        ++i;      } +} + +static dbus_bool_t +pseudorandom_generate_random_bytes (DBusString *str, +                                    int         n_bytes) +{ +  int old_len; +  char *p; +   +  old_len = _dbus_string_get_length (str); + +  if (!_dbus_string_lengthen (str, n_bytes)) +    return FALSE; + +  p = _dbus_string_get_data_len (str, old_len, n_bytes); + +  pseudorandom_generate_random_bytes_buffer (p, n_bytes);    return TRUE; +} - failed: -  _dbus_string_set_length (str, old_len); -  return FALSE; +/** + * Fills n_bytes of the given buffer with random bytes. + * + * @param buffer an allocated buffer + * @param n_bytes the number of bytes in buffer to write to + */ +void +_dbus_generate_random_bytes_buffer (char *buffer, +                                    int   n_bytes) +{ +  DBusString str; + +  if (!_dbus_string_init (&str)) +    return pseudorandom_generate_random_bytes_buffer (buffer, n_bytes); + +  if (!_dbus_generate_random_bytes (&str, n_bytes)) +    { +      _dbus_string_free (&str); +      return pseudorandom_generate_random_bytes_buffer (buffer, n_bytes); +    } + +  _dbus_string_copy_to_buffer (&str, buffer, n_bytes); + +  _dbus_string_free (&str);  }  /** diff --git a/dbus/dbus-sysdeps.h b/dbus/dbus-sysdeps.h index dabf334c..6727630a 100644 --- a/dbus/dbus-sysdeps.h +++ b/dbus/dbus-sysdeps.h @@ -256,10 +256,12 @@ dbus_bool_t  _dbus_directory_get_next_file (DBusDirIter      *iter,  void         _dbus_directory_close         (DBusDirIter      *iter); -dbus_bool_t _dbus_generate_random_bytes (DBusString *str, -                                         int         n_bytes); -dbus_bool_t _dbus_generate_random_ascii (DBusString *str, -                                         int         n_bytes); +void        _dbus_generate_random_bytes_buffer (char       *buffer, +                                                int         n_bytes); +dbus_bool_t _dbus_generate_random_bytes        (DBusString *str, +                                                int         n_bytes); +dbus_bool_t _dbus_generate_random_ascii        (DBusString *str, +                                                int         n_bytes);  const char *_dbus_errno_to_string  (int errnum);  const char* _dbus_error_from_errno (int error_number); diff --git a/doc/dbus-specification.xml b/doc/dbus-specification.xml index 1d47733c..ff625447 100644 --- a/doc/dbus-specification.xml +++ b/doc/dbus-specification.xml @@ -2165,6 +2165,28 @@        The set of optionally-escaped bytes is intended to preserve address         readability and convenience.      </para> + +    <para> +      A server may specify a key-value pair with the key <literal>guid</literal> +      and the value a hex-encoded 16-byte sequence. This globally unique ID must +      be created by filling the first 4 bytes with a 32-bit UNIX time since the +      epoch, and the remaining 12 bytes with random bytes. If present, the GUID +      may be used to distinguish one server from another. A server should use a +      different GUID for each address it listens on. For example, if a message +      bus daemon offers both UNIX domain socket and TCP connections, but treats +      clients the same regardless of how they connect, those two connections are +      equivalent post-connection but should have distinct GUIDs to distinguish +      the kinds of connection. +    </para> +     +    <para> +      The intent of the GUID feature is to allow a client to avoid opening +      multiple identical connections to the same server, by allowing the client +      to check whether an address corresponds to an already-existing connection. +      Comparing two addresses is insufficient, because addresses can be recycled +      by distinct servers. +    </para> +      <para>        [FIXME clarify if attempting to connect to each is a requirement         or just a suggestion]  | 
