| From bca014caaa6130e57f69b5bf527967aa8ee70fdd Mon Sep 17 00:00:00 2001 |
| From: Ben Hutchings <ben@decadent.org.uk> |
| Date: Thu, 28 Apr 2016 09:24:01 +0930 |
| Subject: module: Invalidate signatures on force-loaded modules |
| |
| From: Ben Hutchings <ben@decadent.org.uk> |
| |
| commit bca014caaa6130e57f69b5bf527967aa8ee70fdd upstream. |
| |
| Signing a module should only make it trusted by the specific kernel it |
| was built for, not anything else. Loading a signed module meant for a |
| kernel with a different ABI could have interesting effects. |
| Therefore, treat all signatures as invalid when a module is |
| force-loaded. |
| |
| Signed-off-by: Ben Hutchings <ben@decadent.org.uk> |
| Signed-off-by: Rusty Russell <rusty@rustcorp.com.au> |
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |
| |
| --- |
| kernel/module.c | 13 +++++++++---- |
| 1 file changed, 9 insertions(+), 4 deletions(-) |
| |
| --- a/kernel/module.c |
| +++ b/kernel/module.c |
| @@ -2606,13 +2606,18 @@ static inline void kmemleak_load_module( |
| #endif |
| |
| #ifdef CONFIG_MODULE_SIG |
| -static int module_sig_check(struct load_info *info) |
| +static int module_sig_check(struct load_info *info, int flags) |
| { |
| int err = -ENOKEY; |
| const unsigned long markerlen = sizeof(MODULE_SIG_STRING) - 1; |
| const void *mod = info->hdr; |
| |
| - if (info->len > markerlen && |
| + /* |
| + * Require flags == 0, as a module with version information |
| + * removed is no longer the module that was signed |
| + */ |
| + if (flags == 0 && |
| + info->len > markerlen && |
| memcmp(mod + info->len - markerlen, MODULE_SIG_STRING, markerlen) == 0) { |
| /* We truncate the module to discard the signature */ |
| info->len -= markerlen; |
| @@ -2631,7 +2636,7 @@ static int module_sig_check(struct load_ |
| return err; |
| } |
| #else /* !CONFIG_MODULE_SIG */ |
| -static int module_sig_check(struct load_info *info) |
| +static int module_sig_check(struct load_info *info, int flags) |
| { |
| return 0; |
| } |
| @@ -3444,7 +3449,7 @@ static int load_module(struct load_info |
| long err; |
| char *after_dashes; |
| |
| - err = module_sig_check(info); |
| + err = module_sig_check(info, flags); |
| if (err) |
| goto free_copy; |
| |