lkml.org 
[lkml]   [2020]   [Mar]   [17]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH 5.5 046/151] devlink: validate length of param values
    Date
    From: Jakub Kicinski <kuba@kernel.org>

    [ Upstream commit 8750939b6ad86abc3f53ec8a9683a1cded4a5654 ]

    DEVLINK_ATTR_PARAM_VALUE_DATA may have different types
    so it's not checked by the normal netlink policy. Make
    sure the attribute length is what we expect.

    Fixes: e3b7ca18ad7b ("devlink: Add param set command")
    Signed-off-by: Jakub Kicinski <kuba@kernel.org>
    Reviewed-by: Jiri Pirko <jiri@mellanox.com>
    Signed-off-by: David S. Miller <davem@davemloft.net>
    Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
    ---
    net/core/devlink.c | 31 +++++++++++++++++++------------
    1 file changed, 19 insertions(+), 12 deletions(-)

    --- a/net/core/devlink.c
    +++ b/net/core/devlink.c
    @@ -3352,34 +3352,41 @@ devlink_param_value_get_from_info(const
    struct genl_info *info,
    union devlink_param_value *value)
    {
    + struct nlattr *param_data;
    int len;

    - if (param->type != DEVLINK_PARAM_TYPE_BOOL &&
    - !info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA])
    + param_data = info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA];
    +
    + if (param->type != DEVLINK_PARAM_TYPE_BOOL && !param_data)
    return -EINVAL;

    switch (param->type) {
    case DEVLINK_PARAM_TYPE_U8:
    - value->vu8 = nla_get_u8(info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA]);
    + if (nla_len(param_data) != sizeof(u8))
    + return -EINVAL;
    + value->vu8 = nla_get_u8(param_data);
    break;
    case DEVLINK_PARAM_TYPE_U16:
    - value->vu16 = nla_get_u16(info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA]);
    + if (nla_len(param_data) != sizeof(u16))
    + return -EINVAL;
    + value->vu16 = nla_get_u16(param_data);
    break;
    case DEVLINK_PARAM_TYPE_U32:
    - value->vu32 = nla_get_u32(info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA]);
    + if (nla_len(param_data) != sizeof(u32))
    + return -EINVAL;
    + value->vu32 = nla_get_u32(param_data);
    break;
    case DEVLINK_PARAM_TYPE_STRING:
    - len = strnlen(nla_data(info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA]),
    - nla_len(info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA]));
    - if (len == nla_len(info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA]) ||
    + len = strnlen(nla_data(param_data), nla_len(param_data));
    + if (len == nla_len(param_data) ||
    len >= __DEVLINK_PARAM_MAX_STRING_VALUE)
    return -EINVAL;
    - strcpy(value->vstr,
    - nla_data(info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA]));
    + strcpy(value->vstr, nla_data(param_data));
    break;
    case DEVLINK_PARAM_TYPE_BOOL:
    - value->vbool = info->attrs[DEVLINK_ATTR_PARAM_VALUE_DATA] ?
    - true : false;
    + if (param_data && nla_len(param_data))
    + return -EINVAL;
    + value->vbool = nla_get_flag(param_data);
    break;
    }
    return 0;

    \
     
     \ /
      Last update: 2020-03-17 12:17    [W:2.515 / U:3.296 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site