[dm-devel] [PATCH 3/5] multipath-tools: New way to limit the IPC command length.

Christophe Varoqui christophe.varoqui at opensvc.com
Fri Feb 10 11:36:04 UTC 2017


Applied.

On Fri, Jan 20, 2017 at 2:39 PM, Gris Ge <fge at redhat.com> wrote:

> Problem:
>
>     mpath_recv_reply() from libmpathcmd return -EINVAL on command 'show
>     maps json' with 2k paths.  No error will be triggered for command
>     `multipathd -k'show maps json` as multipathd is using their own
>     implementation on recv_packet() which does not have size limitation.
>
> Root cause:
>
>     Commit 174e717d351789a3cb29e1417f8e910baabcdb16 introduced the
>     limitation on max bytes(65535) of reply string from multipathd.
>     With 2k paths(1k mpaths) simulated by scsi_debug, the 'show maps json'
>     requires 2066784 bytes which trigged the EINVAL error.
>
> Fix:
>     * Remove the limitation of MAX_REPLY_LEN in libmpathcmd.
>
>     * New functions `recv_packet_from_client()` in uxsock.h of libmultipath
>       which enforce the limitation of buffer size to 512(_MAX_CMD_LEN).
>
>     * Change multipathd socket listener to use
>       `recv_packet_from_client()`.
>
> Signed-off-by: Gris Ge <fge at redhat.com>
> ---
>  libmpathcmd/mpath_cmd.c |  2 --
>  libmultipath/uxsock.c   | 39 ++++++++++++++++++++++++++++++---------
>  libmultipath/uxsock.h   |  9 +++++++++
>  multipathd/uxlsnr.c     |  8 +++++---
>  4 files changed, 44 insertions(+), 14 deletions(-)
>
> diff --git a/libmpathcmd/mpath_cmd.c b/libmpathcmd/mpath_cmd.c
> index d9c5790..7fc9e98 100644
> --- a/libmpathcmd/mpath_cmd.c
> +++ b/libmpathcmd/mpath_cmd.c
> @@ -142,8 +142,6 @@ int mpath_recv_reply(int fd, char **reply, unsigned
> int timeout)
>         len = mpath_recv_reply_len(fd, timeout);
>         if (len <= 0)
>                 return len;
> -       if (len > MAX_REPLY_LEN)
> -               return -EINVAL;
>         *reply = malloc(len);
>         if (!*reply)
>                 return -1;
> diff --git a/libmultipath/uxsock.c b/libmultipath/uxsock.c
> index 0ca9e50..492f4b9 100644
> --- a/libmultipath/uxsock.c
> +++ b/libmultipath/uxsock.c
> @@ -24,6 +24,16 @@
>  #include "memory.h"
>  #include "uxsock.h"
>  #include "debug.h"
> +
> +/*
> + * Code is similar with mpath_recv_reply() with data size limitation
> + * and debug-able malloc.
> + * When limit == 0, it means no limit on data size, used for socket client
> + * to receiving data from multipathd.
> + */
> +static int _recv_packet(int fd, char **buf, unsigned int timeout,
> +                       ssize_t limit);
> +
>  /*
>   * create a unix domain socket and start listening on it
>   * return a file descriptor open on the socket
> @@ -81,26 +91,37 @@ int send_packet(int fd, const char *buf)
>         return mpath_send_cmd(fd, buf);
>  }
>
> -/*
> - * receive a packet in length prefix format
> - */
> -int recv_packet(int fd, char **buf, unsigned int timeout)
> +static int _recv_packet(int fd, char **buf, unsigned int timeout, ssize_t
> limit)
>  {
> -       int err;
> -       ssize_t len;
> +       int err = 0;
> +       ssize_t len = 0;
>
>         *buf = NULL;
>         len = mpath_recv_reply_len(fd, timeout);
>         if (len <= 0)
>                 return len;
> +       if ((limit > 0) && (len > limit))
> +               return -EINVAL;
>         (*buf) = MALLOC(len);
>         if (!*buf)
>                 return -ENOMEM;
>         err = mpath_recv_reply_data(fd, *buf, len, timeout);
> -       if (err) {
> +       if (err != 0) {
>                 FREE(*buf);
>                 (*buf) = NULL;
> -               return err;
>         }
> -       return 0;
> +       return err;
> +}
> +
> +/*
> + * receive a packet in length prefix format
> + */
> +int recv_packet(int fd, char **buf, unsigned int timeout)
> +{
> +       return _recv_packet(fd, buf, timeout, 0 /* no limit */);
> +}
> +
> +int recv_packet_from_client(int fd, char **buf, unsigned int timeout)
> +{
> +       return _recv_packet(fd, buf, timeout, _MAX_CMD_LEN);
>  }
> diff --git a/libmultipath/uxsock.h b/libmultipath/uxsock.h
> index 442b564..8e7401d 100644
> --- a/libmultipath/uxsock.h
> +++ b/libmultipath/uxsock.h
> @@ -2,3 +2,12 @@
>  int ux_socket_listen(const char *name);
>  int send_packet(int fd, const char *buf);
>  int recv_packet(int fd, char **buf, unsigned int timeout);
> +
> +#define _MAX_CMD_LEN           512
> +
> +/*
> + * Used for receiving socket command from untrusted socket client where
> data
> + * size is restricted to 512(_MAX_CMD_LEN) at most.
> + * Return -EINVAL if data length requested by client exceeded the
> _MAX_CMD_LEN.
> + */
> +int recv_packet_from_client(int fd, char **buf, unsigned int timeout);
> diff --git a/multipathd/uxlsnr.c b/multipathd/uxlsnr.c
> index dfef03e..6ca62af 100644
> --- a/multipathd/uxlsnr.c
> +++ b/multipathd/uxlsnr.c
> @@ -241,13 +241,15 @@ void * uxsock_listen(uxsock_trigger_fn
> uxsock_trigger, void * trigger_data)
>                                 if (clock_gettime(CLOCK_MONOTONIC,
> &start_time)
>                                     != 0)
>                                         start_time.tv_sec = 0;
> -                               if (recv_packet(c->fd, &inbuf,
> -                                               uxsock_timeout) != 0) {
> +                               if (recv_packet_from_client(c->fd, &inbuf,
> +                                                           uxsock_timeout)
> +                                   != 0) {
>                                         dead_client(c);
>                                         continue;
>                                 }
>                                 if (!inbuf) {
> -                                       condlog(4, "recv_packet get null
> request");
> +                                       condlog(4,
> "recv_packet_from_client "
> +                                               "get null request");
>                                         continue;
>                                 }
>                                 condlog(4, "cli[%d]: Got request [%s]",
> --
> 1.8.3.1
>
> --
> dm-devel mailing list
> dm-devel at redhat.com
> https://www.redhat.com/mailman/listinfo/dm-devel
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://listman.redhat.com/archives/dm-devel/attachments/20170210/eaf55a7a/attachment.htm>


More information about the dm-devel mailing list