[syslog-ng] [PATCH] [1/1] Add support for Unix sockets.

Balazs Scheidler bazsi at balabit.hu
Tue Aug 14 12:31:31 CEST 2012


Hi,

Algernon is the master for libmongo-client, so he'd have to ACK on that
part. I was running through the patch, so I figured I'll share my
comments for what it's worth.

On Sun, 2012-08-12 at 03:57 +0200, Conrad Hoffmann wrote:
> Add a separate connect function to both mongo-client and mongo-sync
> and demonstrate usage by adding this feature to the mongo-dump
> example program.
> 
> Replica sets have no support for Unix sockets so far.
> 
> Signed-off-by: Conrad Hoffmann <ch at bitfehler.net>
> ---
>  examples/mongo-dump.c | 22 +++++++++++++++++-----
>  src/mongo-client.c    | 40 ++++++++++++++++++++++++++++++++++++++++
>  src/mongo-client.h    | 12 ++++++++++++
>  src/mongo-sync.c      | 23 +++++++++++++++++++++++
>  src/mongo-sync.h      | 15 +++++++++++++++
>  5 files changed, 107 insertions(+), 5 deletions(-)
> 
> diff --git a/src/mongo-client.c b/src/mongo-client.c
> index ed931e4..67f9b64 100644
> --- a/src/mongo-client.c
> +++ b/src/mongo-client.c
> @@ -109,6 +110,45 @@ mongo_connect (const char *host, int port)
>    return conn;
>  }
>  
> +mongo_connection *
> +mongo_unix_connect (const char *path)
> +{
> +  int len, fd = -1;
> +  mongo_connection *conn;
> +  struct sockaddr_un remote;
> +
> +  if (!path)
> +    {
> +      errno = EINVAL;
> +      return NULL;
> +    }
> +
> +  conn = g_new0 (mongo_connection, 1);
> +
> +  fd = socket (AF_UNIX, SOCK_STREAM, 0);
> +  if (fd == -1)
> +    {
> +      errno = EADDRNOTAVAIL;
> +      return NULL;
> +    }
> +
> +  remote.sun_family = AF_UNIX;
> +  strcpy(remote.sun_path, path);

this could be a buffer overflow, if path is longer than the char array
in the sockaddr_un struct.

> +  len = strlen(remote.sun_path) + sizeof(remote.sun_family);

and this clearly has an assumption on the contents of the sockaddr_un
struct.

sizeof(remote) should also work, but if you really want to support very
long path names for the unix domain socket (e.g. ones that exceed 108
chars, the limit in struct sockaddr_un), you'd have to allocate "remote"
dynamically, and I'm not completely sure it'd actually work.

And look what I've found while reading sys/un.h:

/* Evaluate to actual length of the `sockaddr_un' structure.  */
# define SUN_LEN(ptr) ((size_t) (((struct sockaddr_un *) 0)->sun_path)        \
                      + strlen ((ptr)->sun_path))

I'm not sure that's portable though.

> +  if (connect(fd, (struct sockaddr *)&remote, len) == -1)
> +    {
> +      close(fd);
> +      g_free (conn);
> +
> +      errno = EADDRNOTAVAIL;
> +      return NULL;
> +    }
> +
> +  conn->fd = fd;
> +
> +  return conn;
> +}
> +
>  void
>  mongo_disconnect (mongo_connection *conn)
>  {
> diff --git a/src/mongo-client.h b/src/mongo-client.h
> index 28863e5..3917b05 100644
> --- a/src/mongo-client.h
> +++ b/src/mongo-client.h
> @@ -50,6 +50,18 @@ typedef struct _mongo_connection mongo_connection;
>   */
>  mongo_connection *mongo_connect (const char *host, int port);
>  
> +/** Connect to a MongoDB server via a Unix socket.
> + *
> + * Connects to a single MongoDB server using a Unix Domain Socket.
> + *
> + * @param path is the path of the Unix socket.
> + *
> + * @returns A newly allocated mongo_connection object or NULL on
> + * error. It is the responsibility of the caller to free it once it is
> + * not used anymore.
> + */
> +mongo_connection *mongo_unix_connect (const char *path);
> +
>  /** Disconnect from a MongoDB server.
>   *
>   * @param conn is the connection object to disconnect from.
> diff --git a/src/mongo-sync.c b/src/mongo-sync.c
> index ab3ae16..ce26245 100644
> --- a/src/mongo-sync.c
> +++ b/src/mongo-sync.c
> @@ -51,6 +51,29 @@ mongo_sync_connect (const gchar *host, gint port,
>    return s;
>  }
>  
> +mongo_sync_connection *
> +mongo_sync_unix_connect (const gchar *path, gboolean slaveok)
> +{
> +  mongo_sync_connection *s;
> +  mongo_connection *c;
> +
> +  c = mongo_unix_connect (path);
> +  if (!c)
> +    return NULL;
> +  s = g_realloc (c, sizeof (mongo_sync_connection));
> +
> +  s->slaveok = slaveok;
> +  s->safe_mode = FALSE;
> +  s->auto_reconnect = FALSE;
> +  s->rs.seeds = NULL;
> +  s->rs.hosts = NULL;
> +  s->rs.primary = NULL;
> +  s->last_error = NULL;
> +  s->max_insert_size = MONGO_SYNC_DEFAULT_MAX_INSERT_SIZE;
> +
> +  return s;
> +}
> +
>  gboolean
>  mongo_sync_conn_seed_add (mongo_sync_connection *conn,
>  			  const gchar *host, gint port)
> diff --git a/src/mongo-sync.h b/src/mongo-sync.h
> index bc4f50e..515062a 100644
> --- a/src/mongo-sync.h
> +++ b/src/mongo-sync.h
> @@ -67,6 +67,21 @@ mongo_sync_connection *mongo_sync_connect (const gchar *host,
>  					   gint port,
>  					   gboolean slaveok);
>  
> +/** Synchronously connect to a MongoDB server via Unix socket.
> + *
> + * Sets up a synchronous connection to a MongoDB server.
> + *
> + * @param path is the path to the Unix Domain Socket to connect to.
> + * @param slaveok signals whether queries made against a slave are
> + * acceptable.
> + *
> + * @returns A newly allocated mongo_sync_connection object, or NULL on
> + * error. It is the responsibility of the caller to close and free the
> + * connection when appropriate.
> + */
> +mongo_sync_connection *mongo_sync_unix_connect (const gchar *host,
> +						gboolean slaveok);
> +
>  /** Add a seed to an existing MongoDB connection.
>   *
>   * The seed list will be used for reconnects, prioritized before the

-- 
Bazsi




More information about the syslog-ng mailing list