forked from xuos/xiuos
merge codes
This commit is contained in:
parent
21f454fd87
commit
93ad360a1a
|
@ -153,4 +153,9 @@ bool semaphore_wait(int sem_id)
|
||||||
bool semaphore_signal(int sem_id)
|
bool semaphore_signal(int sem_id)
|
||||||
{
|
{
|
||||||
return syscall(SYSCALL_SEMAPHORE, (intptr_t)SYS_SEM_SIGNAL, (intptr_t)sem_id, 0, 0);
|
return syscall(SYSCALL_SEMAPHORE, (intptr_t)SYS_SEM_SIGNAL, (intptr_t)sem_id, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
int sleep(intptr_t ms)
|
||||||
|
{
|
||||||
|
return syscall(SYSCALL_SLEEP, (intptr_t)ms, 0, 0, 0);
|
||||||
}
|
}
|
|
@ -34,6 +34,7 @@
|
||||||
#define SYSCALL_KILL 12 // kill the task by id
|
#define SYSCALL_KILL 12 // kill the task by id
|
||||||
|
|
||||||
#define SYSCALL_SEMAPHORE 13 // semaphore related operations
|
#define SYSCALL_SEMAPHORE 13 // semaphore related operations
|
||||||
|
#define SYSCALL_SLEEP 14 // sleep
|
||||||
// clang-format on
|
// clang-format on
|
||||||
|
|
||||||
typedef enum {
|
typedef enum {
|
||||||
|
@ -105,4 +106,6 @@ uintptr_t get_tick();
|
||||||
int semaphore_new(int val);
|
int semaphore_new(int val);
|
||||||
bool semaphore_free(int sem_id);
|
bool semaphore_free(int sem_id);
|
||||||
bool semaphore_wait(int sem_id);
|
bool semaphore_wait(int sem_id);
|
||||||
bool semaphore_signal(int sem_id);
|
bool semaphore_signal(int sem_id);
|
||||||
|
|
||||||
|
int sleep(intptr_t ms);
|
|
@ -48,6 +48,7 @@ Modification:
|
||||||
#define SYSCALL_KILL 12 // kill the task by id
|
#define SYSCALL_KILL 12 // kill the task by id
|
||||||
|
|
||||||
#define SYSCALL_SEMAPHORE 13 // semaphore related operations
|
#define SYSCALL_SEMAPHORE 13 // semaphore related operations
|
||||||
|
#define SYSCALL_SLEEP 14 // sleep
|
||||||
// clang-format on
|
// clang-format on
|
||||||
|
|
||||||
#ifndef __ASSEMBLER__
|
#ifndef __ASSEMBLER__
|
||||||
|
@ -113,4 +114,5 @@ int sys_unbind_irq_all(struct Thread* task);
|
||||||
int sys_unbind_irq(struct Thread* task, int irq_num);
|
int sys_unbind_irq(struct Thread* task, int irq_num);
|
||||||
|
|
||||||
int sys_semaphore(sys_sem_option op, int sem_id);
|
int sys_semaphore(sys_sem_option op, int sem_id);
|
||||||
|
int sys_sleep(intptr_t ms);
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -44,6 +44,7 @@ Modification:
|
||||||
#define TASK_MAX_PRIORITY 32
|
#define TASK_MAX_PRIORITY 32
|
||||||
#define TASK_DEFAULT_PRIORITY 2
|
#define TASK_DEFAULT_PRIORITY 2
|
||||||
#define TASK_NAME_MAX_LEN 16
|
#define TASK_NAME_MAX_LEN 16
|
||||||
|
#define SLEEP_MONITOR_CORE 0
|
||||||
|
|
||||||
enum ProcState {
|
enum ProcState {
|
||||||
INIT = 0,
|
INIT = 0,
|
||||||
|
@ -51,6 +52,7 @@ enum ProcState {
|
||||||
RUNNING,
|
RUNNING,
|
||||||
DEAD,
|
DEAD,
|
||||||
BLOCKED,
|
BLOCKED,
|
||||||
|
SLEEPING,
|
||||||
NEVER_RUN,
|
NEVER_RUN,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -72,6 +74,10 @@ struct ThreadContext {
|
||||||
struct trapframe* trapframe;
|
struct trapframe* trapframe;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct TaskSleepContext {
|
||||||
|
int64_t remain_ms;
|
||||||
|
};
|
||||||
|
|
||||||
/* Process Control Block */
|
/* Process Control Block */
|
||||||
struct Thread {
|
struct Thread {
|
||||||
/* task name */
|
/* task name */
|
||||||
|
@ -97,6 +103,7 @@ struct Thread {
|
||||||
|
|
||||||
/* task schedule attributes */
|
/* task schedule attributes */
|
||||||
struct double_list_node node;
|
struct double_list_node node;
|
||||||
|
struct TaskSleepContext sleep_context;
|
||||||
enum ProcState state;
|
enum ProcState state;
|
||||||
int priority; // priority
|
int priority; // priority
|
||||||
int remain_tick;
|
int remain_tick;
|
||||||
|
@ -114,6 +121,7 @@ struct XiziTaskManager {
|
||||||
struct double_list_node task_list_head[TASK_MAX_PRIORITY]; /* list of task control blocks that are allocated */
|
struct double_list_node task_list_head[TASK_MAX_PRIORITY]; /* list of task control blocks that are allocated */
|
||||||
struct double_list_node task_running_list_head;
|
struct double_list_node task_running_list_head;
|
||||||
struct double_list_node task_blocked_list_head;
|
struct double_list_node task_blocked_list_head;
|
||||||
|
struct double_list_node task_sleep_list_head;
|
||||||
struct XiziSemaphorePool semaphore_pool;
|
struct XiziSemaphorePool semaphore_pool;
|
||||||
|
|
||||||
/* mem allocator */
|
/* mem allocator */
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
SRC_FILES := syscall.c \
|
SRC_FILES := syscall.c \
|
||||||
sys_spawn.c \
|
sys_spawn.c \
|
||||||
sys_thread.c \
|
sys_thread.c \
|
||||||
|
sys_sleep.c \
|
||||||
sys_yield.c \
|
sys_yield.c \
|
||||||
sys_register_as_server.c \
|
sys_register_as_server.c \
|
||||||
sys_connect_session.c \
|
sys_connect_session.c \
|
||||||
|
|
|
@ -91,6 +91,12 @@ void show_tasks(void)
|
||||||
SHOWTASK_TASK_BASE_INFO(task);
|
SHOWTASK_TASK_BASE_INFO(task);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DOUBLE_LIST_FOR_EACH_ENTRY(task, &xizi_task_manager.task_sleep_list_head, node)
|
||||||
|
{
|
||||||
|
LOG_PRINTF("%-8s", "SLEEP");
|
||||||
|
SHOWTASK_TASK_BASE_INFO(task);
|
||||||
|
}
|
||||||
|
|
||||||
struct ksemaphore* sem = NULL;
|
struct ksemaphore* sem = NULL;
|
||||||
DOUBLE_LIST_FOR_EACH_ENTRY(sem, &xizi_task_manager.semaphore_pool.sem_list_guard, sem_list_node)
|
DOUBLE_LIST_FOR_EACH_ENTRY(sem, &xizi_task_manager.semaphore_pool.sem_list_guard, sem_list_node)
|
||||||
{
|
{
|
||||||
|
|
|
@ -80,6 +80,9 @@ int syscall(int sys_num, uintptr_t param1, uintptr_t param2, uintptr_t param3, u
|
||||||
case SYSCALL_SEMAPHORE:
|
case SYSCALL_SEMAPHORE:
|
||||||
ret = sys_semaphore((sys_sem_option)param1, (int)param2);
|
ret = sys_semaphore((sys_sem_option)param1, (int)param2);
|
||||||
break;
|
break;
|
||||||
|
case SYSCALL_SLEEP:
|
||||||
|
ret = sys_sleep((intptr_t)param1);
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
ERROR("Unsurport syscall(%d) right now\n", sys_num);
|
ERROR("Unsurport syscall(%d) right now\n", sys_num);
|
||||||
ret = -1;
|
ret = -1;
|
||||||
|
|
|
@ -38,6 +38,7 @@ Modification:
|
||||||
#include "scheduler.h"
|
#include "scheduler.h"
|
||||||
#include "syscall.h"
|
#include "syscall.h"
|
||||||
#include "task.h"
|
#include "task.h"
|
||||||
|
#include "trap_common.h"
|
||||||
|
|
||||||
struct CPU global_cpus[NR_CPU];
|
struct CPU global_cpus[NR_CPU];
|
||||||
uint32_t ready_task_priority;
|
uint32_t ready_task_priority;
|
||||||
|
@ -70,6 +71,7 @@ static void _task_manager_init()
|
||||||
}
|
}
|
||||||
doubleListNodeInit(&xizi_task_manager.task_blocked_list_head);
|
doubleListNodeInit(&xizi_task_manager.task_blocked_list_head);
|
||||||
doubleListNodeInit(&xizi_task_manager.task_running_list_head);
|
doubleListNodeInit(&xizi_task_manager.task_running_list_head);
|
||||||
|
doubleListNodeInit(&xizi_task_manager.task_sleep_list_head);
|
||||||
// init task (slab) allocator
|
// init task (slab) allocator
|
||||||
slab_init(&xizi_task_manager.memspace_allocator, sizeof(struct MemSpace));
|
slab_init(&xizi_task_manager.memspace_allocator, sizeof(struct MemSpace));
|
||||||
slab_init(&xizi_task_manager.task_allocator, sizeof(struct Thread));
|
slab_init(&xizi_task_manager.task_allocator, sizeof(struct Thread));
|
||||||
|
@ -286,6 +288,7 @@ extern void context_switch(struct context**, struct context*);
|
||||||
static void _scheduler(struct SchedulerRightGroup right_group)
|
static void _scheduler(struct SchedulerRightGroup right_group)
|
||||||
{
|
{
|
||||||
struct MmuCommonDone* p_mmu_driver = AchieveResource(&right_group.mmu_driver_tag);
|
struct MmuCommonDone* p_mmu_driver = AchieveResource(&right_group.mmu_driver_tag);
|
||||||
|
// struct XiziTrapDriver* p_intr_driver = AchieveResource(&right_group.intr_driver_tag);
|
||||||
struct Thread* next_task;
|
struct Thread* next_task;
|
||||||
struct CPU* cpu = cur_cpu();
|
struct CPU* cpu = cur_cpu();
|
||||||
|
|
||||||
|
@ -347,7 +350,7 @@ static void _task_block(struct double_list_node* head, struct Thread* task)
|
||||||
static void _task_unblock(struct Thread* task)
|
static void _task_unblock(struct Thread* task)
|
||||||
{
|
{
|
||||||
assert(task != NULL);
|
assert(task != NULL);
|
||||||
assert(task->state == BLOCKED);
|
assert(task->state == BLOCKED || task->state == SLEEPING);
|
||||||
task_node_leave_list(task);
|
task_node_leave_list(task);
|
||||||
task->state = READY;
|
task->state = READY;
|
||||||
task_node_add_to_ready_list_back(task);
|
task_node_add_to_ready_list_back(task);
|
||||||
|
|
|
@ -69,6 +69,8 @@ int xizi_clock_handler(int irq, void* tf, void* arg)
|
||||||
if (p_clock_driver->is_timer_expired()) {
|
if (p_clock_driver->is_timer_expired()) {
|
||||||
p_clock_driver->clear_clock_intr();
|
p_clock_driver->clear_clock_intr();
|
||||||
global_tick++;
|
global_tick++;
|
||||||
|
|
||||||
|
// handle current thread
|
||||||
struct Thread* current_task = cur_cpu()->task;
|
struct Thread* current_task = cur_cpu()->task;
|
||||||
if (current_task) {
|
if (current_task) {
|
||||||
current_task->remain_tick--;
|
current_task->remain_tick--;
|
||||||
|
@ -77,6 +79,18 @@ int xizi_clock_handler(int irq, void* tf, void* arg)
|
||||||
xizi_task_manager.task_yield_noschedule(current_task, false);
|
xizi_task_manager.task_yield_noschedule(current_task, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// todo: cpu 0 will handle sleeping thread
|
||||||
|
struct Thread* thread = NULL;
|
||||||
|
DOUBLE_LIST_FOR_EACH_ENTRY(thread, &xizi_task_manager.task_sleep_list_head, node)
|
||||||
|
{
|
||||||
|
assert(thread->state == SLEEPING);
|
||||||
|
thread->sleep_context.remain_ms--;
|
||||||
|
if (thread->sleep_context.remain_ms <= 0) {
|
||||||
|
xizi_task_manager.task_unblock(thread);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
Loading…
Reference in New Issue