:: commit 84ac96435e7ae183644830c02a22cefec62f8f80

mintsuki <mintsuki@protonmail.com> — 2020-03-28 03:02

parents: 44a5f47516

Add bump allocator

diff --git a/src/drivers/disk.c b/src/drivers/disk.c
index f94e1488..0aebbab1 100644
--- a/src/drivers/disk.c
+++ b/src/drivers/disk.c
@@ -9,12 +9,10 @@
 #define SECTOR_SIZE 512
 #define BLOCK_SIZE_IN_SECTORS 16
 #define BLOCK_SIZE  (SECTOR_SIZE * BLOCK_SIZE_IN_SECTORS)
-#define BUFFER_SEG  0x7000
-#define BUFFER_OFF  0
-#define BUFFER_ADDR ((uint8_t *)((BUFFER_SEG << 4) + BUFFER_OFF))
 
 #define CACHE_INVALID (~((uint64_t)0))
 
+static uint8_t *cache        = NULL;
 static uint64_t cached_block = CACHE_INVALID;
 
 static struct {
@@ -23,13 +21,18 @@ static struct {
     uint16_t offset;
     uint16_t segment;
     uint64_t lba;
-} dap = { 16, BLOCK_SIZE_IN_SECTORS, BUFFER_OFF, BUFFER_SEG, 0 };
+} dap = { 16, BLOCK_SIZE_IN_SECTORS, 0, 0, 0 };
 
 static int cache_block(int drive, uint64_t block) {
     if (block == cached_block)
         return 0;
 
-    dap.lba = block * BLOCK_SIZE_IN_SECTORS;
+    if (!cache)
+        cache = balloc(BLOCK_SIZE);
+
+    dap.segment = rm_seg(cache);
+    dap.offset  = rm_off(cache);
+    dap.lba     = block * BLOCK_SIZE_IN_SECTORS;
 
     struct rm_regs r = {0};
     r.eax = 0x4200;
@@ -64,7 +67,7 @@ int read(int drive, void *buffer, uint64_t loc, uint64_t count) {
         if (chunk > BLOCK_SIZE - offset)
             chunk = BLOCK_SIZE - offset;
 
-        memcpy(buffer + progress, &BUFFER_ADDR[offset], chunk);
+        memcpy(buffer + progress, &cache[offset], chunk);
         progress += chunk;
     }
 
diff --git a/src/fs/echfs.c b/src/fs/echfs.c
index 6f8698c0..7b36ec4d 100644
--- a/src/fs/echfs.c
+++ b/src/fs/echfs.c
@@ -16,8 +16,6 @@ struct echfs_identity_table {
 #define END_OF_CHAIN (~((uint64_t)0))
 #define FILE_TYPE    0
 
-#define CACHE_ADDR   ((uint8_t *)(0x30000))
-
 static int cache_block(struct echfs_file_handle *file, uint64_t block) {
     // Load the file.
     uint64_t block_val = file->dir_entry.payload;
@@ -33,7 +31,7 @@ sizeof(uint64_t));
     if (block_val == END_OF_CHAIN)
         return -1;
 
-    return read_partition(file->disk, &file->mbr_part, CACHE_ADDR, block_val * file->block_size, file->block_size);
+    return read_partition(file->disk, &file->mbr_part, file->cache, block_val * file->block_size, file->block_size);
 }
 
 int echfs_read(struct echfs_file_handle *file, void *buf, uint64_t loc, uint64_t count) {
@@ -50,7 +48,7 @@ int echfs_read(struct echfs_file_handle *file, void *buf, uint64_t loc, uint64_t
         if (chunk > file->block_size - offset)
             chunk = file->block_size - offset;
 
-        memcpy(buf + progress, &CACHE_ADDR[offset], chunk);
+        memcpy(buf + progress, &file->cache[offset], chunk);
         progress += chunk;
     }
 
@@ -76,6 +74,7 @@ int echfs_open(struct echfs_file_handle *ret, int disk, int partition, const cha
     ret->alloc_table_size   = DIV_ROUNDUP(ret->block_count * sizeof(uint64_t), ret->block_size) * ret->block_size;
     ret->alloc_table_offset = 16 * ret->block_size;
     ret->dir_offset         = ret->alloc_table_offset + ret->alloc_table_size;
+    ret->cache              = balloc(ret->block_size);
 
     // Find the file in the root dir.
     for (uint64_t i = 0; i < ret->dir_length; i += sizeof(struct echfs_dir_entry)) {
diff --git a/src/fs/echfs.h b/src/fs/echfs.h
index 369212de..c03e02b7 100644
--- a/src/fs/echfs.h
+++ b/src/fs/echfs.h
@@ -27,6 +27,7 @@ struct echfs_file_handle {
     uint64_t alloc_table_size;
     uint64_t alloc_table_offset;
     uint64_t dir_offset;
+    uint8_t *cache;
     struct echfs_dir_entry dir_entry;
 };
 
diff --git a/src/lib/blib.c b/src/lib/blib.c
index 55496d6f..26191d0b 100644
--- a/src/lib/blib.c
+++ b/src/lib/blib.c
@@ -8,6 +8,25 @@
 #include <lib/libc.h>
 #include <lib/cio.h>
 
+static size_t bump_allocator_base = 0x20000;
+
+void *balloc(size_t count) {
+    void *ret = (void *)bump_allocator_base;
+    bump_allocator_base += count;
+    return ret;
+}
+
+// Only power of 2 alignments
+void *balloc_aligned(size_t count, size_t alignment) {
+    if (bump_allocator_base & (alignment - 1)) {
+        bump_allocator_base &= ~(alignment - 1);
+        bump_allocator_base += alignment;
+    }
+    void *ret = (void *)bump_allocator_base;
+    bump_allocator_base += count;
+    return ret;
+}
+
 void pit_sleep(uint64_t pit_ticks) {
     uint64_t target = global_pit_tick + pit_ticks;
     while (global_pit_tick < target) {
diff --git a/src/lib/blib.h b/src/lib/blib.h
index 24c3ffdd..20083b73 100644
--- a/src/lib/blib.h
+++ b/src/lib/blib.h
@@ -7,6 +7,9 @@
 void pit_sleep(uint64_t pit_ticks);
 int pit_sleep_and_quit_on_keypress(uint64_t pit_ticks);
 
+void *balloc(size_t count);
+void *balloc_aligned(size_t count, size_t alignment);
+
 #define GETCHAR_CURSOR_LEFT  (-10)
 #define GETCHAR_CURSOR_RIGHT (-11)
 #define GETCHAR_CURSOR_UP    (-12)
diff --git a/src/main.c b/src/main.c
index 3b22f19a..4070e140 100644
--- a/src/main.c
+++ b/src/main.c
@@ -38,6 +38,8 @@ void main(int boot_drive) {
     print("qLoader 2\n\n");
     print("=> Boot drive: %x\n", boot_drive);
 
+    void *config_addr = balloc(4096);
+
     // Enumerate partitions.
     struct mbr_part parts[4];
     for (int i = 0; i < 4; i++) {
@@ -49,7 +51,7 @@ void main(int boot_drive) {
             print("   Found!\n");
             if (!config_loaded) {
                 if (!echfs_open(&f, boot_drive, i, CONFIG_NAME)) {
-                    echfs_read(&f, (void *)0x100000, 0, f.dir_entry.size);
+                    echfs_read(&f, config_addr, 0, f.dir_entry.size);
                     config_loaded = 1;
                     print("   Config file found and loaded!\n");
                 }
@@ -62,22 +64,22 @@ void main(int boot_drive) {
 
     if (config_loaded) {
         char buf[32];
-        if (!config_get_value(buf, 32, (void*)0x100000, "KERNEL_DRIVE")) {
+        if (!config_get_value(buf, 32, config_addr, "KERNEL_DRIVE")) {
             print("KERNEL_DRIVE not specified, using boot drive (%x)", boot_drive);
             drive = boot_drive;
         } else {
             drive = (int)strtoui(buf);
         }
-        if (!config_get_value(buf, 64, (void*)0x100000, "TIMEOUT")) {
+        if (!config_get_value(buf, 64, config_addr, "TIMEOUT")) {
             timeout = 5;
         } else {
             timeout = (int)strtoui(buf);
         }
-        config_get_value(buf, 32, (void*)0x100000, "KERNEL_PARTITION");
+        config_get_value(buf, 32, config_addr, "KERNEL_PARTITION");
         part = (int)strtoui(buf);
-        config_get_value(path, 128, (void*)0x100000, "KERNEL_PATH");
-        config_get_value(cmdline, 128, (void*)0x100000, "KERNEL_CMDLINE");
-        config_get_value(proto, 64, (void*)0x100000, "KERNEL_PROTO");
+        config_get_value(path, 128, config_addr, "KERNEL_PATH");
+        config_get_value(cmdline, 128, config_addr, "KERNEL_CMDLINE");
+        config_get_value(proto, 64, config_addr, "KERNEL_PROTO");
     } else {
         print("   !! NO CONFIG FILE FOUND ON BOOT DRIVE !!");
         for (;;);
diff --git a/src/protos/stivale.c b/src/protos/stivale.c
index 2d902234..3c8dd7e1 100644
--- a/src/protos/stivale.c
+++ b/src/protos/stivale.c
@@ -79,7 +79,7 @@ void stivale_load(struct echfs_file_handle *fd) {
                  &stivale_struct.framebuffer_bpp);
     }
 
-    volatile struct {
+    struct pagemap {
         uint64_t pml4[512];
         uint64_t pml3_lo[512];
         uint64_t pml3_hi[512];
@@ -87,7 +87,8 @@ void stivale_load(struct echfs_file_handle *fd) {
         uint64_t pml2_1gb[512];
         uint64_t pml2_2gb[512];
         uint64_t pml2_3gb[512];
-    } *pagemap = (void *)0x20000;
+    };
+    struct pagemap *pagemap = balloc_aligned(sizeof(struct pagemap), 0x1000);
 
     // first, zero out the pagemap
     for (uint64_t *p = (uint64_t *)pagemap; p < &pagemap->pml3_hi[512]; p++)
tab: 248 wrap: offon