rt: Use an enum to represent the task state
This commit is contained in:
parent
0201a03203
commit
05466c6138
@ -61,7 +61,7 @@ extern "C" CDECL void
|
||||
record_sp(void *limit);
|
||||
|
||||
// Tasks
|
||||
rust_task::rust_task(rust_task_thread *thread, rust_task_list *state,
|
||||
rust_task::rust_task(rust_task_thread *thread, rust_task_state state,
|
||||
rust_task *spawner, const char *name,
|
||||
size_t init_stack_sz) :
|
||||
ref_count(1),
|
||||
@ -231,7 +231,7 @@ rust_task::start(spawn_fn spawnee_fn,
|
||||
|
||||
void rust_task::start()
|
||||
{
|
||||
transition(&thread->newborn_tasks, &thread->running_tasks, NULL, "none");
|
||||
transition(task_state_newborn, task_state_running, NULL, "none");
|
||||
}
|
||||
|
||||
bool
|
||||
@ -350,14 +350,14 @@ bool
|
||||
rust_task::running()
|
||||
{
|
||||
scoped_lock with(state_lock);
|
||||
return state == &thread->running_tasks;
|
||||
return state == task_state_running;
|
||||
}
|
||||
|
||||
bool
|
||||
rust_task::blocked()
|
||||
{
|
||||
scoped_lock with(state_lock);
|
||||
return state == &thread->blocked_tasks;
|
||||
return state == task_state_blocked;
|
||||
}
|
||||
|
||||
bool
|
||||
@ -371,7 +371,7 @@ bool
|
||||
rust_task::dead()
|
||||
{
|
||||
scoped_lock with(state_lock);
|
||||
return state == &thread->dead_tasks;
|
||||
return state == task_state_dead;
|
||||
}
|
||||
|
||||
void *
|
||||
@ -393,13 +393,13 @@ rust_task::free(void *p)
|
||||
}
|
||||
|
||||
void
|
||||
rust_task::transition(rust_task_list *src, rust_task_list *dst,
|
||||
rust_task::transition(rust_task_state src, rust_task_state dst,
|
||||
rust_cond *cond, const char* cond_name) {
|
||||
thread->transition(this, src, dst, cond, cond_name);
|
||||
}
|
||||
|
||||
void
|
||||
rust_task::set_state(rust_task_list *state,
|
||||
rust_task::set_state(rust_task_state state,
|
||||
rust_cond *cond, const char* cond_name) {
|
||||
scoped_lock with(state_lock);
|
||||
this->state = state;
|
||||
@ -421,7 +421,7 @@ rust_task::block(rust_cond *on, const char* name) {
|
||||
A(thread, cond == NULL, "Cannot block an already blocked task.");
|
||||
A(thread, on != NULL, "Cannot block on a NULL object.");
|
||||
|
||||
transition(&thread->running_tasks, &thread->blocked_tasks, on, name);
|
||||
transition(task_state_running, task_state_blocked, on, name);
|
||||
|
||||
return true;
|
||||
}
|
||||
@ -433,12 +433,12 @@ rust_task::wakeup(rust_cond *from) {
|
||||
(uintptr_t) cond, (uintptr_t) from);
|
||||
A(thread, cond == from, "Cannot wake up blocked task on wrong condition.");
|
||||
|
||||
transition(&thread->blocked_tasks, &thread->running_tasks, NULL, "none");
|
||||
transition(task_state_blocked, task_state_running, NULL, "none");
|
||||
}
|
||||
|
||||
void
|
||||
rust_task::die() {
|
||||
transition(&thread->running_tasks, &thread->dead_tasks, NULL, "none");
|
||||
transition(task_state_running, task_state_dead, NULL, "none");
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -90,7 +90,7 @@ private:
|
||||
|
||||
// Protects state, cond, cond_name
|
||||
lock_and_signal state_lock;
|
||||
rust_task_list *state;
|
||||
rust_task_state state;
|
||||
rust_cond *cond;
|
||||
const char *cond_name;
|
||||
|
||||
@ -121,7 +121,7 @@ private:
|
||||
|
||||
void return_c_stack();
|
||||
|
||||
void transition(rust_task_list *src, rust_task_list *dst,
|
||||
void transition(rust_task_state src, rust_task_state dst,
|
||||
rust_cond *cond, const char* cond_name);
|
||||
|
||||
bool must_fail_from_being_killed_unlocked();
|
||||
@ -134,7 +134,7 @@ public:
|
||||
|
||||
// Only a pointer to 'name' is kept, so it must live as long as this task.
|
||||
rust_task(rust_task_thread *thread,
|
||||
rust_task_list *state,
|
||||
rust_task_state state,
|
||||
rust_task *spawner,
|
||||
const char *name,
|
||||
size_t init_stack_sz);
|
||||
@ -152,7 +152,7 @@ public:
|
||||
void *realloc(void *data, size_t sz);
|
||||
void free(void *p);
|
||||
|
||||
void set_state(rust_task_list *state,
|
||||
void set_state(rust_task_state state,
|
||||
rust_cond *cond, const char* cond_name);
|
||||
|
||||
bool block(rust_cond *on, const char* name);
|
||||
@ -206,7 +206,7 @@ public:
|
||||
|
||||
rust_port_selector *get_port_selector() { return &port_selector; }
|
||||
|
||||
rust_task_list *get_state() { return state; }
|
||||
rust_task_state get_state() { return state; }
|
||||
rust_cond *get_cond() { return cond; }
|
||||
const char *get_cond_name() { return cond_name; }
|
||||
};
|
||||
|
@ -27,13 +27,13 @@ rust_task_thread::rust_task_thread(rust_scheduler *sched,
|
||||
id(id),
|
||||
should_exit(false),
|
||||
cached_c_stack(NULL),
|
||||
kernel(sched->kernel),
|
||||
sched(sched),
|
||||
srv(srv),
|
||||
newborn_tasks(this, "newborn"),
|
||||
running_tasks(this, "running"),
|
||||
blocked_tasks(this, "blocked"),
|
||||
dead_tasks(this, "dead"),
|
||||
kernel(sched->kernel),
|
||||
sched(sched),
|
||||
srv(srv),
|
||||
log_lvl(log_debug),
|
||||
min_stack_size(kernel->env->min_stack_size),
|
||||
env(kernel->env),
|
||||
@ -248,7 +248,7 @@ rust_task_thread::start_main_loop() {
|
||||
", state: %s",
|
||||
scheduled_task->name,
|
||||
(uintptr_t)scheduled_task,
|
||||
scheduled_task->get_state()->name);
|
||||
state_list(scheduled_task->get_state())->name);
|
||||
|
||||
place_task_in_tls(scheduled_task);
|
||||
|
||||
@ -262,7 +262,7 @@ rust_task_thread::start_main_loop() {
|
||||
" in state '%s', worker id=%d" PRIxPTR,
|
||||
scheduled_task->name,
|
||||
(uintptr_t)scheduled_task,
|
||||
scheduled_task->get_state()->name,
|
||||
state_list(scheduled_task->get_state())->name,
|
||||
id);
|
||||
|
||||
reap_dead_tasks();
|
||||
@ -289,7 +289,7 @@ rust_task_thread::create_task(rust_task *spawner, const char *name,
|
||||
size_t init_stack_sz) {
|
||||
rust_task *task =
|
||||
new (this->kernel, "rust_task")
|
||||
rust_task (this, &newborn_tasks, spawner, name, init_stack_sz);
|
||||
rust_task (this, task_state_newborn, spawner, name, init_stack_sz);
|
||||
DLOG(this, task, "created task: " PTR ", spawner: %s, name: %s",
|
||||
task, spawner ? spawner->name : "null", name);
|
||||
|
||||
@ -302,18 +302,34 @@ rust_task_thread::create_task(rust_task *spawner, const char *name,
|
||||
return task;
|
||||
}
|
||||
|
||||
rust_task_list *
|
||||
rust_task_thread::state_list(rust_task_state state) {
|
||||
switch (state) {
|
||||
case task_state_newborn:
|
||||
return &newborn_tasks;
|
||||
case task_state_running:
|
||||
return &running_tasks;
|
||||
case task_state_blocked:
|
||||
return &blocked_tasks;
|
||||
case task_state_dead:
|
||||
return &dead_tasks;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
rust_task_thread::transition(rust_task *task,
|
||||
rust_task_list *src, rust_task_list *dst,
|
||||
rust_task_state src, rust_task_state dst,
|
||||
rust_cond *cond, const char* cond_name) {
|
||||
scoped_lock with(lock);
|
||||
rust_task_list *src_list = state_list(src);
|
||||
rust_task_list *dst_list = state_list(dst);
|
||||
DLOG(this, task,
|
||||
"task %s " PTR " state change '%s' -> '%s' while in '%s'",
|
||||
name, (uintptr_t)this, src->name, dst->name,
|
||||
task->get_state()->name);
|
||||
name, (uintptr_t)this, src_list->name, dst_list->name,
|
||||
state_list(task->get_state())->name);
|
||||
I(this, task->get_state() == src);
|
||||
src->remove(task);
|
||||
dst->append(task);
|
||||
src_list->remove(task);
|
||||
dst_list->append(task);
|
||||
task->set_state(dst, cond, cond_name);
|
||||
|
||||
lock.signal();
|
||||
|
@ -1,6 +1,7 @@
|
||||
#ifndef RUST_TASK_THREAD_H
|
||||
#define RUST_TASK_THREAD_H
|
||||
|
||||
#include "rust_internal.h"
|
||||
#include "sync/rust_thread.h"
|
||||
#include "rust_stack.h"
|
||||
#include "context.h"
|
||||
@ -11,6 +12,13 @@
|
||||
#include <windows.h>
|
||||
#endif
|
||||
|
||||
enum rust_task_state {
|
||||
task_state_newborn,
|
||||
task_state_running,
|
||||
task_state_blocked,
|
||||
task_state_dead
|
||||
};
|
||||
|
||||
struct rust_task_thread : public kernel_owned<rust_task_thread>,
|
||||
rust_thread
|
||||
{
|
||||
@ -37,19 +45,21 @@ private:
|
||||
stk_seg *cached_c_stack;
|
||||
stk_seg *extra_c_stack;
|
||||
|
||||
rust_task_list newborn_tasks;
|
||||
rust_task_list running_tasks;
|
||||
rust_task_list blocked_tasks;
|
||||
rust_task_list dead_tasks;
|
||||
|
||||
void prepare_c_stack(rust_task *task);
|
||||
void unprepare_c_stack();
|
||||
|
||||
rust_task_list *state_list(rust_task_state state);
|
||||
|
||||
public:
|
||||
rust_kernel *kernel;
|
||||
rust_scheduler *sched;
|
||||
rust_srv *srv;
|
||||
|
||||
rust_task_list newborn_tasks;
|
||||
rust_task_list running_tasks;
|
||||
rust_task_list blocked_tasks;
|
||||
rust_task_list dead_tasks;
|
||||
|
||||
// NB: this is used to filter *runtime-originating* debug
|
||||
// logging, on a per-scheduler basis. It's not likely what
|
||||
// you want to expose to the user in terms of per-task
|
||||
@ -90,7 +100,7 @@ public:
|
||||
size_t init_stack_sz);
|
||||
|
||||
void transition(rust_task *task,
|
||||
rust_task_list *src, rust_task_list *dst,
|
||||
rust_task_state src, rust_task_state dst,
|
||||
rust_cond *cond, const char* cond_name);
|
||||
|
||||
virtual void run();
|
||||
|
Loading…
Reference in New Issue
Block a user