feat: add threading to Scheduler, fix desktop background selection freeze issue
This commit is contained in:
@@ -0,0 +1,101 @@
|
||||
/*
|
||||
* main.cpp
|
||||
* Threading smoke test for MontaukOS.
|
||||
* Copyright (c) 2026 Daniel Hammer
|
||||
*
|
||||
* Spawns two worker threads that increment a shared counter under a
|
||||
* userspace mutex, joins them, and reports the result.
|
||||
*/
|
||||
|
||||
#include <montauk/syscall.h>
|
||||
#include <montauk/thread.h>
|
||||
|
||||
using montauk::Mutex;
|
||||
|
||||
static constexpr int ITERS_PER_THREAD = 100000;
|
||||
|
||||
struct WorkerState {
|
||||
Mutex* lock;
|
||||
int* counter;
|
||||
int delta;
|
||||
};
|
||||
|
||||
static int worker(void* raw) {
|
||||
auto* s = (WorkerState*)raw;
|
||||
for (int i = 0; i < ITERS_PER_THREAD; i++) {
|
||||
s->lock->lock();
|
||||
*(s->counter) += s->delta;
|
||||
s->lock->unlock();
|
||||
}
|
||||
return s->delta;
|
||||
}
|
||||
|
||||
static void print_int(int v) {
|
||||
char buf[16];
|
||||
int n = 0;
|
||||
if (v == 0) {
|
||||
buf[n++] = '0';
|
||||
} else {
|
||||
bool neg = v < 0;
|
||||
unsigned int u = neg ? (unsigned int)(-(long long)v) : (unsigned int)v;
|
||||
char tmp[16]; int t = 0;
|
||||
while (u) { tmp[t++] = (char)('0' + (u % 10)); u /= 10; }
|
||||
if (neg) buf[n++] = '-';
|
||||
while (t) buf[n++] = tmp[--t];
|
||||
}
|
||||
buf[n] = '\0';
|
||||
montauk::print(buf);
|
||||
}
|
||||
|
||||
extern "C" void _start() {
|
||||
Mutex lock;
|
||||
int counter = 0;
|
||||
|
||||
WorkerState a{&lock, &counter, +1};
|
||||
WorkerState b{&lock, &counter, +2};
|
||||
|
||||
int tidA = montauk::thread_spawn(worker, &a);
|
||||
int tidB = montauk::thread_spawn(worker, &b);
|
||||
if (tidA < 0 || tidB < 0) {
|
||||
montauk::print("threadtest: spawn failed\n");
|
||||
montauk::exit(1);
|
||||
}
|
||||
|
||||
montauk::print("threadtest: spawned tids ");
|
||||
print_int(tidA);
|
||||
montauk::print(" and ");
|
||||
print_int(tidB);
|
||||
montauk::print("\n");
|
||||
|
||||
int codeA = -1, codeB = -1;
|
||||
if (montauk::thread_join(tidA, &codeA) != 0) {
|
||||
montauk::print("threadtest: join A failed\n");
|
||||
montauk::exit(2);
|
||||
}
|
||||
if (montauk::thread_join(tidB, &codeB) != 0) {
|
||||
montauk::print("threadtest: join B failed\n");
|
||||
montauk::exit(3);
|
||||
}
|
||||
|
||||
int expected = ITERS_PER_THREAD * (1 + 2);
|
||||
montauk::print("threadtest: counter=");
|
||||
print_int(counter);
|
||||
montauk::print(" expected=");
|
||||
print_int(expected);
|
||||
montauk::print(" codes=");
|
||||
print_int(codeA);
|
||||
montauk::print("/");
|
||||
print_int(codeB);
|
||||
montauk::print("\n");
|
||||
|
||||
if (counter != expected) {
|
||||
montauk::print("threadtest: FAIL (counter mismatch)\n");
|
||||
montauk::exit(4);
|
||||
}
|
||||
if (codeA != 1 || codeB != 2) {
|
||||
montauk::print("threadtest: FAIL (exit codes)\n");
|
||||
montauk::exit(5);
|
||||
}
|
||||
montauk::print("threadtest: PASS\n");
|
||||
montauk::exit(0);
|
||||
}
|
||||
Reference in New Issue
Block a user