summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorMarvin Borner2021-07-07 00:40:28 +0200
committerMarvin Borner2021-07-07 00:40:28 +0200
commit736d2b820d968915516d1662b84f9995d53895a3 (patch)
treee38c1f01be3d0d5e99677c921b971f543b586240
parentb2880945ae17ad857bd425540acd3dc75b2cff6b (diff)
Started graphical selection interface
-rw-r--r--src/loader/cfg.c89
-rw-r--r--src/loader/inc/cfg.h16
-rw-r--r--src/loader/inc/impl/all.h2
-rw-r--r--src/loader/inc/log.h1
-rw-r--r--src/loader/inc/sel.h8
-rw-r--r--src/loader/log.c15
-rw-r--r--src/loader/main.c6
-rw-r--r--src/loader/sel.c20
8 files changed, 102 insertions, 55 deletions
diff --git a/src/loader/cfg.c b/src/loader/cfg.c
index a55533e..9f2e06a 100644
--- a/src/loader/cfg.c
+++ b/src/loader/cfg.c
@@ -10,16 +10,8 @@
#define TIMEOUT "TIMEOUT"
#define PATH "PATH"
-// Config struct (gettable using cfg_get)
-struct {
- u32 timeout;
- struct {
- u8 exists : 1;
- char name[64];
- char path[64];
- struct dev *dev;
- } elem[16]; // Up to 16 different selections
-} cfg = { 0 };
+// Config structure
+static struct cfg cfg = { 0 };
// Config file contents (if found)
static char file[1024] = { 0 };
@@ -38,29 +30,30 @@ static u8 cfg_find(struct dev *dev)
return 0;
}
-// Checks if index is appropriate as some key/value need to be in element
-static void cfg_in_element(u8 index)
+// Checks if index is appropriate as some key/value need to be in entry
+static void cfg_in_entry(u8 index)
{
if (index == 0xff)
- panic("No element name given\n");
+ panic("No entry name given\n");
}
-// Add/overwrite value by key and element index
+// Add/overwrite value by key and entry index
static void cfg_add(u8 index, enum cfg_key key, const char *value)
{
- cfg.elem[index].exists = 1;
+ struct cfg_entry *entry = &cfg.entry[index];
+ entry->exists = 1;
switch (key) {
case CFG_NAME:
- cfg_in_element(index);
- strlcpy(cfg.elem[index].name, value, sizeof(cfg.elem[index].name));
+ cfg_in_entry(index);
+ strlcpy(entry->name, value, sizeof(entry->name));
break;
case CFG_TIMEOUT:
cfg.timeout = atoi(value);
break;
case CFG_PATH:
- cfg_in_element(index);
- strlcpy(cfg.elem[index].path, value, sizeof(cfg.elem[index].path));
+ cfg_in_entry(index);
+ strlcpy(entry->path, value, sizeof(entry->path));
break;
case CFG_NONE:
default:
@@ -68,27 +61,12 @@ static void cfg_add(u8 index, enum cfg_key key, const char *value)
}
}
-const void *cfg_get(u8 index, enum cfg_key key)
-{
- switch (key) {
- case CFG_NAME:
- return &cfg.elem[index].path;
- case CFG_TIMEOUT:
- return &cfg.timeout;
- case CFG_PATH:
- return &cfg.elem[index].path;
- case CFG_NONE:
- default:
- return NULL;
- }
-}
-
// TODO: This code is kind of messy
// Structure per line: KEY=VALUE
static void cfg_parse(void)
{
- // Element index
- u8 elem = 0xff;
+ // Entry index
+ u8 entry = 0xff;
// Value per key
char value[64] = { 0 };
@@ -96,7 +74,7 @@ static void cfg_parse(void)
// States
enum cfg_key current = CFG_NONE; // Value key type
- u8 state = 0; // 0 is key, 1 is value, 2 is elem
+ u8 state = 0; // 0 is key, 1 is value, 2 is entry
const char *start = file; // Start is at the beginning of the key
for (const char *p = start; *p; p++) {
@@ -105,7 +83,7 @@ static void cfg_parse(void)
if (*p == '\n') { // A key can't just end but ok
start = p + 1;
} else if (*p == '#') {
- state = 2; // Let's parse the element name
+ state = 2; // Let's parse the entry name
p++;
continue;
} else if (*p != '=') {
@@ -133,7 +111,7 @@ static void cfg_parse(void)
assert(value_index + 1 < (u8)sizeof(value));
if (*p == '\n') { // Finished
value[value_index] = 0;
- cfg_add(elem, current, value);
+ cfg_add(entry, current, value);
value_index = 0;
state = 0;
p--; // Repeat parse normally
@@ -141,12 +119,12 @@ static void cfg_parse(void)
value[value_index++] = *p;
}
} else if (state == 2) {
- // We're at element name parsing
+ // We're at entry name parsing
assert(value_index + 1 < (u8)sizeof(value));
if (*p == '\n') { // Finished
- elem = elem == 0xff ? 0 : elem + 1;
+ entry = entry == 0xff ? 0 : entry + 1;
value[value_index] = 0;
- cfg_add(elem, CFG_NAME, value);
+ cfg_add(entry, CFG_NAME, value);
value_index = 0;
state = 0;
p--; // Repeat parse normally
@@ -170,18 +148,20 @@ static u8 cfg_path_disk(const char *path)
// Find matching disk dev for every entry and verify path existence and readability
static void cfg_verify(void)
{
- for (u8 i = 0; i < COUNT(cfg.elem) && cfg.elem[i].exists; i++) {
- u8 len = cfg_path_disk(cfg.elem[i].path);
- struct dev *dev = dev_get_by_name(cfg.elem[i].path, len);
+ for (u8 i = 0; i < COUNT(cfg.entry) && cfg.entry[i].exists; i++) {
+ struct cfg_entry *entry = &cfg.entry[i];
+
+ u8 len = cfg_path_disk(entry->path);
+ struct dev *dev = dev_get_by_name(entry->path, len);
if (!dev || dev->type != DEV_DISK)
panic("Invalid device in config\n");
- cfg.elem[i].dev = dev;
+ entry->dev = dev;
if (!dev->p.disk.fs.read)
panic("Device fs not readable\n");
// This is now the correct path (due to "disk:PATH")
- const char *path = &cfg.elem[i].path[len + 1];
+ const char *path = &entry->path[len + 1];
u8 buf[1] = { 0 }; // Just for existence-check
s32 ret = dev->p.disk.fs.read(path, buf, 0, sizeof(buf), dev);
@@ -193,16 +173,25 @@ static void cfg_verify(void)
}
}
+// Call cb for each entry config
+void cfg_foreach(u8 (*cb)(struct cfg_entry *))
+{
+ for (u8 i = 0; i < COUNT(cfg.entry) && cfg.entry[i].exists; i++) {
+ if (cb(&cfg.entry[i])) // 1 means break
+ break;
+ }
+}
+
// Print all configs and entry values
static void cfg_print(void)
{
log("[CFG] Global: %d\n", cfg.timeout);
- for (u8 i = 0; i < COUNT(cfg.elem) && cfg.elem[i].exists; i++)
- log("[CFG] Element: %s at %s\n", cfg.elem[i].name, cfg.elem[i].path);
+ for (u8 i = 0; i < COUNT(cfg.entry) && cfg.entry[i].exists; i++)
+ log("[CFG] Entry: %s at %s\n", cfg.entry[i].name, cfg.entry[i].path);
}
-void cfg_exec(void)
+void cfg_read(void)
{
dev_foreach(DEV_DISK, &cfg_find);
if (!file[0])
diff --git a/src/loader/inc/cfg.h b/src/loader/inc/cfg.h
index 1332fe1..27b3ca3 100644
--- a/src/loader/inc/cfg.h
+++ b/src/loader/inc/cfg.h
@@ -15,7 +15,19 @@ enum cfg_key {
CFG_PATH,
};
-const void *cfg_get(u8 index, enum cfg_key key);
-void cfg_exec(void);
+struct cfg_entry {
+ u8 exists : 1;
+ char name[64];
+ char path[64];
+ struct dev *dev;
+};
+
+struct cfg {
+ u32 timeout;
+ struct cfg_entry entry[16]; // Up to 16 different entries
+};
+
+void cfg_foreach(u8 (*cb)(struct cfg_entry *));
+void cfg_read(void);
#endif
diff --git a/src/loader/inc/impl/all.h b/src/loader/inc/impl/all.h
index 366b1b3..1568322 100644
--- a/src/loader/inc/impl/all.h
+++ b/src/loader/inc/impl/all.h
@@ -11,9 +11,11 @@ enum impl_type {
IMPL_MB2,
};
+struct dev;
struct impl {
enum impl_type type;
void *start; // Of header/entry
+ void (*load)(struct dev *, const char *);
};
#include <dev.h>
diff --git a/src/loader/inc/log.h b/src/loader/inc/log.h
index 6fad366..c40ce50 100644
--- a/src/loader/inc/log.h
+++ b/src/loader/inc/log.h
@@ -9,5 +9,6 @@ void serial_print(const char *data);
void vga_clear(void);
void log(const char *format, ...);
+void vga_log(const char *format, ...);
#endif
diff --git a/src/loader/inc/sel.h b/src/loader/inc/sel.h
new file mode 100644
index 0000000..3885d34
--- /dev/null
+++ b/src/loader/inc/sel.h
@@ -0,0 +1,8 @@
+// MIT License, Copyright (c) 2021 Marvin Borner
+
+#ifndef SEL_H
+#define SEL_H
+
+void sel_draw(void);
+
+#endif
diff --git a/src/loader/log.c b/src/loader/log.c
index b0f03b9..a22f5d2 100644
--- a/src/loader/log.c
+++ b/src/loader/log.c
@@ -150,9 +150,10 @@ static void vga_print(const char *data)
}
/**
- * Universal print function
+ * Formatted print functions
*/
+// Serial
void log(const char *format, ...)
{
char buf[1024] = { 0 };
@@ -163,5 +164,17 @@ void log(const char *format, ...)
va_end(ap);
serial_print(buf);
+}
+
+// VGA log
+void vga_log(const char *format, ...)
+{
+ char buf[1024] = { 0 };
+
+ va_list ap;
+ va_start(ap, format);
+ vsnprintf(buf, sizeof(buf), format, ap);
+ va_end(ap);
+
vga_print(buf);
}
diff --git a/src/loader/main.c b/src/loader/main.c
index bb12c80..aa8e62d 100644
--- a/src/loader/main.c
+++ b/src/loader/main.c
@@ -9,6 +9,7 @@
#include <log.h>
#include <pci.h>
#include <pic.h>
+#include <sel.h>
/**
* Entry
@@ -23,11 +24,12 @@ int start(void)
pic_install();
idt_install();
- acpi_probe();
+ // acpi_probe(); // TODO: Fix slow ACPI probing
pci_probe();
dev_print();
- cfg_exec();
+ cfg_read();
+ sel_draw();
// Sleep and wait for interrupts
while (1)
diff --git a/src/loader/sel.c b/src/loader/sel.c
new file mode 100644
index 0000000..c4303a4
--- /dev/null
+++ b/src/loader/sel.c
@@ -0,0 +1,20 @@
+// MIT License, Copyright (c) 2021 Marvin Borner
+// Selection interface
+
+#include <cfg.h>
+#include <def.h>
+#include <log.h>
+#include <sel.h>
+
+static u8 sel_entry(struct cfg_entry *entry)
+{
+ vga_log("> '%s' (%s)\n", entry->name, entry->path);
+ return 0;
+}
+
+void sel_draw(void)
+{
+ vga_clear();
+
+ cfg_foreach(&sel_entry);
+}