lkml.org 
[lkml]   [2017]   [Apr]   [5]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    Subject[PATCH 24/24] Lock down module params that specify hardware parameters (eg. ioport)
    From
    Date
    Provided an annotation for module parameters that specify hardware
    parameters (such as io ports, iomem addresses, irqs, dma channels, fixed
    dma buffers and other types).

    Suggested-by: Alan Cox <gnomes@lxorguk.ukuu.org.uk>
    Signed-off-by: David Howells <dhowells@redhat.com>
    ---

    kernel/params.c | 27 ++++++++++++++++++++++-----
    1 file changed, 22 insertions(+), 5 deletions(-)

    diff --git a/kernel/params.c b/kernel/params.c
    index a6d6149c0fe6..04185c5aa929 100644
    --- a/kernel/params.c
    +++ b/kernel/params.c
    @@ -108,13 +108,20 @@ bool parameq(const char *a, const char *b)
    return parameqn(a, b, strlen(a)+1);
    }

    -static void param_check_unsafe(const struct kernel_param *kp)
    +static bool param_check_unsafe(const struct kernel_param *kp,
    + const char *doing)
    {
    if (kp->flags & KERNEL_PARAM_FL_UNSAFE) {
    pr_warn("Setting dangerous option %s - tainting kernel\n",
    kp->name);
    add_taint(TAINT_USER, LOCKDEP_STILL_OK);
    }
    +
    + if (kp->flags & KERNEL_PARAM_FL_HWPARAM && kernel_is_locked_down()) {
    + pr_err("Command line-specified device addresses, irqs and dma channels are not permitted when the kernel is locked down (%s.%s)\n", doing, kp->name);
    + return false;
    + }
    + return true;
    }

    static int parse_one(char *param,
    @@ -144,8 +151,10 @@ static int parse_one(char *param,
    pr_debug("handling %s with %p\n", param,
    params[i].ops->set);
    kernel_param_lock(params[i].mod);
    - param_check_unsafe(&params[i]);
    - err = params[i].ops->set(val, &params[i]);
    + if (param_check_unsafe(&params[i], doing))
    + err = params[i].ops->set(val, &params[i]);
    + else
    + err = -EPERM;
    kernel_param_unlock(params[i].mod);
    return err;
    }
    @@ -608,6 +617,12 @@ static ssize_t param_attr_show(struct module_attribute *mattr,
    return count;
    }

    +#ifdef CONFIG_MODULES
    +#define mod_name(mod) (mod)->name
    +#else
    +#define mod_name(mod) "unknown"
    +#endif
    +
    /* sysfs always hands a nul-terminated string in buf. We rely on that. */
    static ssize_t param_attr_store(struct module_attribute *mattr,
    struct module_kobject *mk,
    @@ -620,8 +635,10 @@ static ssize_t param_attr_store(struct module_attribute *mattr,
    return -EPERM;

    kernel_param_lock(mk->mod);
    - param_check_unsafe(attribute->param);
    - err = attribute->param->ops->set(buf, attribute->param);
    + if (param_check_unsafe(attribute->param, mod_name(mk->mod)))
    + err = attribute->param->ops->set(buf, attribute->param);
    + else
    + err = -EPERM;
    kernel_param_unlock(mk->mod);
    if (!err)
    return len;
    \
     
     \ /
      Last update: 2017-04-05 22:19    [W:3.613 / U:0.224 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site