:: commit 13900624949c7841ad05a4656b74928df0d70d77

mintsuki <mintsuki@protonmail.com> — 2020-11-07 21:21

parents: 03413047c3

linux: Add possibility to load multiple modules

diff --git a/CONFIG.md b/CONFIG.md
index 760bea51..c86909b2 100644
--- a/CONFIG.md
+++ b/CONFIG.md
@@ -39,7 +39,10 @@ Some keys take *URIs* as values; these are described in the next section.
 *Locally assignable (protocol specific)* keys are:
 * Linux protocol:
   * `KERNEL_PATH` - The URI path of the kernel.
-  * `INITRD_PATH` - The URI path to the initial ramdisk.
+  * `MODULE_PATH` - The URI path to a module (such as initramfs).
+
+  Note that one can define this last variable multiple times to specify multiple
+  modules.
 * stivale and stivale2 protocols:
   * `KERNEL_PATH` - The URI path of the kernel.
   * `MODULE_PATH` - The URI path to a module.
diff --git a/limine-pxe.bin b/limine-pxe.bin
index 66287d00..40301f0b 100644
Binary files a/limine-pxe.bin and b/limine-pxe.bin differ
diff --git a/limine.bin b/limine.bin
index 94aa765e..8dbce093 100644
Binary files a/limine.bin and b/limine.bin differ
diff --git a/stage2/protos/linux.c b/stage2/protos/linux.c
index be91c436..dedb4777 100644
--- a/stage2/protos/linux.c
+++ b/stage2/protos/linux.c
@@ -127,20 +127,28 @@ void linux_load(char *cmdline) {
     memmap_alloc_range(KERNEL_LOAD_ADDR, kernel->size - real_mode_code_size, 0);
     fread(kernel, (void *)KERNEL_LOAD_ADDR, real_mode_code_size, kernel->size - real_mode_code_size);
 
-    char initrd_path[64];
-    if (!config_get_value(initrd_path, 0, 64, "INITRD_PATH"))
-        panic("INITRD_PATH not specified");
+    size_t modules_mem_base = INITRD_LOAD_ADDR;
+    for (size_t i = 0; ; i++) {
+        char module_path[64];
+        if (!config_get_value(module_path, i, 64, "MODULE_PATH"))
+            break;
 
-    struct file_handle initrd;
-    if (!uri_open(&initrd, initrd_path))
-        panic("Could not open initrd");
+        struct file_handle module;
+        if (!uri_open(&module, module_path))
+            panic("Could not open `%s`", module_path);
 
-    print("Loading initrd...\n");
-    memmap_alloc_range(INITRD_LOAD_ADDR, initrd.size, 0);
-    fread(&initrd, (void *)INITRD_LOAD_ADDR, 0, initrd.size);
+        print("Loading module `%s`...\n", module_path);
 
-    *((uint32_t *)(real_mode_code + 0x218)) = (uint32_t)INITRD_LOAD_ADDR;
-    *((uint32_t *)(real_mode_code + 0x21c)) = (uint32_t)initrd.size;
+        memmap_alloc_range(modules_mem_base, module.size, 0);
+        fread(&module, (void *)modules_mem_base, 0, module.size);
+
+        modules_mem_base += module.size;
+    }
+
+    if (modules_mem_base != INITRD_LOAD_ADDR) {
+        *((uint32_t *)(real_mode_code + 0x218)) = (uint32_t)INITRD_LOAD_ADDR;
+        *((uint32_t *)(real_mode_code + 0x21c)) = (uint32_t)(modules_mem_base - INITRD_LOAD_ADDR);
+    }
 
     uint16_t real_mode_code_seg = rm_seg(real_mode_code);
     uint16_t kernel_entry_seg   = real_mode_code_seg + 0x20;
tab: 248 wrap: offon