New logic treats modules without an ELF signature as compressed modules,
since uncompressed kernel modules are ELF files.

This ensures compressed modules are always loaded by syscalls which
support decomperssing, or have been decompressed before loading,
avoiding dmesg like "Invalid ELF header magic: != ELF", which occurs
when loading compressed modules on a kernel without builtin module
decompression.

Signed-off-by: Yao Zi <zi...@disroot.org>
---
 modutils/modutils.c | 32 ++++++++++++++++++++++----------
 1 file changed, 22 insertions(+), 10 deletions(-)

diff --git a/modutils/modutils.c b/modutils/modutils.c
index cbff20961..af3c09194 100644
--- a/modutils/modutils.c
+++ b/modutils/modutils.c
@@ -197,9 +197,10 @@ void* FAST_FUNC try_to_mmap_module(const char *filename, 
size_t *image_size_p)
 int FAST_FUNC bb_init_module(const char *filename, const char *options)
 {
        size_t image_size;
-       char *image;
+       char *image = NULL;
        int rc;
        bool mmaped;
+       bool compressed = 0;
 
        if (!options)
                options = "";
@@ -210,6 +211,20 @@ int FAST_FUNC bb_init_module(const char *filename, const 
char *options)
                return bb_init_module_24(filename, options);
 #endif
 
+       /* Assume compressed module if it is not a valid ELF file */
+       {
+               int fd = open(filename, O_RDONLY | O_CLOEXEC);
+               uint32_t signature;
+
+               if (fd < 0)
+                       goto do_load;
+               if (read(fd, &signature, 4) < 0)
+                       goto do_load;
+
+               compressed = signature != SWAP_BE32(0x7f454c46);
+       }
+
+do_load:
        /*
         * First we try finit_module if available.  Some kernels are configured
         * to only allow loading of modules off of secure storage (like a read-
@@ -220,14 +235,8 @@ int FAST_FUNC bb_init_module(const char *filename, const 
char *options)
        {
                int fd = open(filename, O_RDONLY | O_CLOEXEC);
                if (fd >= 0) {
-                       int flags = is_suffixed_with(filename, ".ko") ? 0 : 
MODULE_INIT_COMPRESSED_FILE;
-                       for (;;) {
-                               rc = finit_module(fd, options, flags);
-                               if (rc == 0 || flags == 0)
-                                       break;
-                               /* Loading non-.ko named uncompressed module? 
Not likely, but let's try it */
-                               flags = 0;
-                       }
+                       int flags = compressed ? MODULE_INIT_COMPRESSED_FILE : 
0;
+                       rc = finit_module(fd, options, flags);
                        close(fd);
                        if (rc == 0)
                                return rc;
@@ -235,9 +244,12 @@ int FAST_FUNC bb_init_module(const char *filename, const 
char *options)
        }
 # endif
 
+       /* Only try mmap with uncompressed modules */
        image_size = INT_MAX - 4095;
        mmaped = 0;
-       image = try_to_mmap_module(filename, &image_size);
+       if (!compressed)
+               image = try_to_mmap_module(filename, &image_size);
+
        if (image) {
                mmaped = 1;
        } else {
-- 
2.45.2

_______________________________________________
busybox mailing list
busybox@busybox.net
http://lists.busybox.net/mailman/listinfo/busybox

Reply via email to