aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorClyne Sullivan <clyne@bitgloo.com>2024-09-27 19:43:17 -0400
committerClyne Sullivan <clyne@bitgloo.com>2024-09-27 19:43:17 -0400
commitbd0acf88361a4b73a49d11a45177e72bf32091bc (patch)
tree86337c40d2430a1c202df785100061666cf72fba
parent35aa65037bebd800f9cba2b558d245552960a5d7 (diff)
fix pit_busy_wait; better tasking
-rw-r--r--kernel.cpp31
-rw-r--r--pit.cpp2
-rw-r--r--tasking.cpp15
-rw-r--r--vgaterminal.cpp2
4 files changed, 40 insertions, 10 deletions
diff --git a/kernel.cpp b/kernel.cpp
index dab93c6..f16faa8 100644
--- a/kernel.cpp
+++ b/kernel.cpp
@@ -10,6 +10,8 @@
static VGATerminal vga;
TextOutput& term = vga;
+static volatile bool termBusy = false;
+
void kernel_main(void)
{
term.write("Clyne's kernel, v2024\n\n");
@@ -28,18 +30,41 @@ void kernel_main(void)
gdt_initialize();
pic_initialize();
idt_initialize();
- pit_initialize(50);
+ pit_initialize(100);
asm volatile("sti");
tasking_initialize();
term.write("Tasking enabled.\n");
tasking_spawn([] {
- for (;;)
+ for (;;) {
+ do pit_busy_wait(1);
+ while (termBusy);
+
+ termBusy = true;
term.write('B');
+ termBusy = false;
+ }
+ }, 256);
+
+ tasking_spawn([] {
+ for (;;) {
+ do pit_busy_wait(1);
+ while (termBusy);
+
+ termBusy = true;
+ term.write('C');
+ termBusy = false;
+ }
}, 256);
- for (;;)
+ for (;;) {
+ do pit_busy_wait(1);
+ while (termBusy);
+
+ termBusy = true;
term.write('A');
+ termBusy = false;
+ }
}
extern "C"
diff --git a/pit.cpp b/pit.cpp
index f3baa4e..6ee5009 100644
--- a/pit.cpp
+++ b/pit.cpp
@@ -33,7 +33,7 @@ void pit_initialize(std::uint32_t frequency)
void pit_busy_wait(std::int32_t tks)
{
const auto end = ticks + tks;
- while (end - ticks > 0)
+ while (static_cast<std::int32_t>(end - ticks) > 0)
asm volatile("nop");
}
diff --git a/tasking.cpp b/tasking.cpp
index 5cfe091..97dd51a 100644
--- a/tasking.cpp
+++ b/tasking.cpp
@@ -7,6 +7,7 @@ struct Task
enum class State {
Invalid,
Staging,
+ Staged,
Running
};
@@ -33,14 +34,14 @@ void schedule(const Registers& regs)
do {
if (++current >= tasks.size())
current = 0;
- } while (tasks[current].state == Task::Invalid);
+ } while (tasks[current].state == Task::Invalid || tasks[current].state == Task::Staging);
asm volatile(R"(
mov %0, %%esp
mov %1, %%ebp
)" :: "m" (tasks[current].esp), "m" (tasks[current].ebp));
- if (tasks[current].state == Task::Staging) {
+ if (tasks[current].state == Task::Staged) {
tasks[current].state = Task::Running;
asm volatile(R"(
pop %eax
@@ -69,7 +70,7 @@ bool tasking_spawn(void (*entry)(), unsigned ssize)
if (i < 0)
return false;
- tasks[i] = Task();
+ tasks[i].state = Task::Staging;
auto stack = reinterpret_cast<std::uint32_t>(new std::uint8_t[ssize]);
const auto stackend = stack + ssize;
@@ -81,9 +82,11 @@ bool tasking_spawn(void (*entry)(), unsigned ssize)
r->cs = 0x8;
asm volatile("pushfl; pop %%eax" : "=a"(r->eflags));
- tasks[i].esp = regbase;
- tasks[i].ebp = stackend;
- tasks[i].state = Task::Staging;
+ tasks[i] = Task {
+ .esp = regbase,
+ .ebp = stackend,
+ .state = Task::Staged
+ };
return true;
}
diff --git a/vgaterminal.cpp b/vgaterminal.cpp
index 8158b14..f2bb081 100644
--- a/vgaterminal.cpp
+++ b/vgaterminal.cpp
@@ -46,9 +46,11 @@ void VGATerminal::checkpos() noexcept
void VGATerminal::updatecursor() const noexcept
{
+ asm volatile("cli");
outb(0x03d4, 0x0f);
outb(0x03d5, static_cast<std::uint8_t>(offset));
outb(0x03d4, 0x0e);
outb(0x03d5, static_cast<std::uint8_t>(offset >> 8));
+ asm volatile("sti");
}