diff --git a/src/include/status.h b/src/include/status.h index 5bdefa3e..e84e2f4c 100644 --- a/src/include/status.h +++ b/src/include/status.h @@ -43,4 +43,6 @@ typedef enum status error_network = -0x0c00, error_user = -0x0d00, error_io = -0x0e00, + error_os = -0x0f00, + error_os_task_overfow = -0x0f01, } status_t; diff --git a/src/include/visor/terravisor/cc_os/cc_os.h b/src/include/visor/terravisor/cc_os/cc_os.h index 043be0be..48af0334 100644 --- a/src/include/visor/terravisor/cc_os/cc_os.h +++ b/src/include/visor/terravisor/cc_os/cc_os.h @@ -1,30 +1,29 @@ #ifndef __CC_OS__ #define __CC_OS__ +#include "status.h" #include "stdint.h" -typedef enum cc_os_err -{ - CC_OS_SUCCESS, - CC_OS_FAIL -}cc_os_err_t; +#define ASSERT_IF_FALSE(con) if(!(con)){return error_func_inval_arg;} + +typedef status_t cc_os_err_t; typedef void (* task_fn)(void * args); typedef struct cc_os_task { task_fn task_fn; - int8_t * i8_name; - int8_t i8_priority; //>> For waited tasks - int32_t * i32_stack_ptr; - size_t s_stack_len; + char * name; + size_t priority; //>> For waited tasks + void * stack_ptr; + size_t stack_len; }cc_os_task_t; cc_os_err_t cc_os_add_task (cc_os_task_t * cc_os_task); -cc_os_err_t cc_os_del_task (int8_t * i8_name); -cc_os_err_t cc_os_pause_task (int8_t * i8_name); -cc_os_err_t cc_os_resume_task (int8_t * i8_name); -cc_os_err_t cc_os_wait_task (uint16_t ticks); +cc_os_err_t cc_os_del_task (char * name); +cc_os_err_t cc_os_pause_task (char * name); +cc_os_err_t cc_os_resume_task (char * name); +cc_os_err_t cc_os_wait_task (size_t ticks); cc_os_err_t cc_os_run (void); #endif /* __CC_OS__ */ diff --git a/src/include/visor/terravisor/cc_os/cc_os_config.h b/src/include/visor/terravisor/cc_os/cc_os_config.h new file mode 100644 index 00000000..cbc05a51 --- /dev/null +++ b/src/include/visor/terravisor/cc_os/cc_os_config.h @@ -0,0 +1,9 @@ +#pragma once + +#ifndef CC_OS_MAX_THREAD +#define CC_OS_MAX_THREAD 10 +#endif + +#ifndef CC_OS_TASK_NAME_LEN +#define CC_OS_TASK_NAME_LEN 16 +#endif diff --git a/src/include/visor/terravisor/cc_os/cc_shed.h b/src/include/visor/terravisor/cc_os/cc_shed.h index c660105d..27096a76 100644 --- a/src/include/visor/terravisor/cc_os/cc_shed.h +++ b/src/include/visor/terravisor/cc_os/cc_shed.h @@ -6,16 +6,18 @@ typedef struct cc_shed_tcb cc_shed_tcb_t; typedef enum { - CC_SHED_TASK_READY, - CC_SHED_TASK_RUNNING, - CC_SHED_TASK_PAUSED, + cc_shed_task_terminated, + cc_shed_task_ready, + cc_shed_task_running, + cc_shed_task_paused, } cc_shed_task_status_t; struct cc_shed_tcb { - int8_t * i8_name; - int8_t i8_priority; - int32_t * i32_sp; + char name [CC_OS_TASK_NAME_LEN]; + size_t priority; + void * stack_ptr; + cc_shed_tcb_t * prev_shed_tcb; cc_shed_tcb_t * next_shed_tcb; cc_shed_task_status_t task_status; }; diff --git a/src/projects/demo_avr/config.mk b/src/projects/demo_avr/config.mk index 3ac7f143..9e3a084e 100644 --- a/src/projects/demo_avr/config.mk +++ b/src/projects/demo_avr/config.mk @@ -14,3 +14,4 @@ FAMILY := mega_avr PLATFORM := atmega328p EARLYCON_SERIAL := 1 CONSOLE_SERIAL := 1 +TERRAKERN := 1 diff --git a/src/visor/terravisor/services/kernel/cc_os.c b/src/visor/terravisor/services/kernel/cc_os.c new file mode 100644 index 00000000..89b2460f --- /dev/null +++ b/src/visor/terravisor/services/kernel/cc_os.c @@ -0,0 +1,176 @@ +#include +#include +#include +#include +#include + +extern cc_shed_tcb_t * g_list_head; +extern cc_shed_tcb_t g_cc_os_tcb_list[]; +extern cc_shed_tcb_t * g_curr_task; + +cc_os_err_t cc_os_add_task (cc_os_task_t * cc_os_task) +{ + ASSERT_IF_FALSE(cc_os_task != NULL); + ASSERT_IF_FALSE(cc_os_task->name != NULL); + ASSERT_IF_FALSE(cc_os_task->stack_ptr != NULL); + ASSERT_IF_FALSE(cc_os_task->task_fn != NULL); + ASSERT_IF_FALSE(cc_os_task->stack_len != 0); + + cc_shed_tcb_t * ptr = g_list_head; + + if ((ptr->next_shed_tcb == NULL )&& (ptr->prev_shed_tcb == NULL)) + { + ptr->next_shed_tcb = ptr->prev_shed_tcb = g_list_head; + } + + else + { + for (size_t i = 0; i < CC_OS_MAX_THREAD; i++) + { + /* Get an available node from global tcb list */ + if (g_cc_os_tcb_list[i].task_status == cc_shed_task_terminated) + { + ptr = &(g_cc_os_tcb_list[i]); + break; + } + } + if (ptr != g_list_head) + { + /* Insert node at last */ + ptr->next_shed_tcb = g_list_head; + g_list_head->prev_shed_tcb = ptr; + ptr->prev_shed_tcb = g_list_head->prev_shed_tcb; + g_list_head->prev_shed_tcb->next_shed_tcb = ptr; + } + else + { + return error_os_task_overfow; + } + + } + /* Fill tcb details */ + memcpy(ptr->name, cc_os_task->name, CC_OS_TASK_NAME_LEN); + ptr->stack_ptr = cc_os_task->stack_ptr; + ptr->priority = cc_os_task->priority; + ptr->task_status = cc_shed_task_ready; + + return success; +} + +cc_os_err_t cc_os_del_task (char * name) +{ + cc_shed_tcb_t * ptr = g_curr_task; + int name_found = 0; + if (name != NULL) + { + /* code to delete node equal to name */ + ptr = g_list_head; + while(ptr->next_shed_tcb != g_list_head) + { + if(strcmp(ptr->name, name) == 0) + { + name_found = 1; + break; + } + } + if (!name_found) + { + return error_func_inval_arg; + } + } + + /* Code to handle first node */ + if (ptr == g_list_head) + { + if (ptr->next_shed_tcb != g_list_head) + { + /* code for more than one node */ + g_list_head = ptr->next_shed_tcb; + } + else + { + /* code for only one node */ + memset(g_list_head, 0, sizeof(cc_shed_tcb_t)); + g_list_head = &(g_cc_os_tcb_list[0]); + return success; + } + + } + + ptr->next_shed_tcb->prev_shed_tcb = ptr->prev_shed_tcb; + ptr->prev_shed_tcb->next_shed_tcb = ptr->next_shed_tcb; + ptr->task_status = cc_shed_task_terminated; + ptr->next_shed_tcb = NULL; + ptr->prev_shed_tcb = NULL; + + return success; +} + +cc_os_err_t cc_os_pause_task (char * name) +{ + cc_shed_tcb_t * ptr = g_curr_task; + int name_found = 0; + if (name != NULL) + { + /* code to pause node equal to name */ + ptr = g_list_head; + while(ptr->next_shed_tcb != g_list_head) + { + if(strcmp(ptr->name, name) == 0) + { + name_found = 1; + break; + } + } + if (!name_found) + { + return error_func_inval_arg; + } + } + + ptr->task_status = cc_shed_task_paused; + + return success; +} + +cc_os_err_t cc_os_resume_task (char * name) +{ + ASSERT_IF_FALSE(name != NULL); + + cc_shed_tcb_t * ptr = g_list_head; + int name_found = 0; + + /* code to resume node equal to name */ + while(ptr->next_shed_tcb != g_list_head) + { + if(strcmp(ptr->name, name) == 0) + { + name_found = 1; + break; + } + } + if (!name_found) + { + return error_func_inval_arg; + } + + ptr->task_status = cc_shed_task_ready; + + return success; +} + +cc_os_err_t cc_os_wait_task (size_t ticks _UNUSED) +{ + return success; +} + +cc_os_err_t cc_os_run (void) +{ + /* OS Init code */ + while (1) + { + /* code to process OS */ + } + + return success; +} diff --git a/src/visor/terravisor/services/kernel/cc_os_shed.c b/src/visor/terravisor/services/kernel/cc_os_shed.c new file mode 100644 index 00000000..56d06e6e --- /dev/null +++ b/src/visor/terravisor/services/kernel/cc_os_shed.c @@ -0,0 +1,6 @@ +#include +#include + +cc_shed_tcb_t g_cc_os_tcb_list [CC_OS_MAX_THREAD]; +cc_shed_tcb_t * g_list_head = &(g_cc_os_tcb_list[0]); +cc_shed_tcb_t * g_curr_task = &(g_cc_os_tcb_list[0]);