kernel: Init back pointer to microkernel task
Fibers initialize this back pointer to NULL as they are (by definition) not microkernel tasks. Microkernel tasks initialize it to their corresponding 'ktask_t'. However for nanokernel systems, the back pointer is always NULL. This is because there is only one task in a nanokernel system (the background task) and it can not pend on a nanokernel object--it must poll. Change-Id: I9840fecc44224bef63d09d587d703720cf33ad57 Signed-off-by: Peter Mitsis <peter.mitsis@windriver.com>
This commit is contained in:
parent
8a33d98811
commit
b58878bb89
8 changed files with 51 additions and 11 deletions
|
@ -101,7 +101,8 @@ static ALWAYS_INLINE void thread_monitor_init(struct tcs *tcs)
|
|||
*
|
||||
* @return N/A
|
||||
*/
|
||||
void _new_thread(char *pStackMem, unsigned stackSize, _thread_entry_t pEntry,
|
||||
void _new_thread(char *pStackMem, unsigned stackSize,
|
||||
void *uk_task_ptr, _thread_entry_t pEntry,
|
||||
void *parameter1, void *parameter2, void *parameter3,
|
||||
int priority, unsigned options)
|
||||
{
|
||||
|
@ -154,6 +155,13 @@ void _new_thread(char *pStackMem, unsigned stackSize, _thread_entry_t pEntry,
|
|||
*/
|
||||
tcs->entry = (struct __thread_entry *)(pInitCtx);
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_MICROKERNEL
|
||||
tcs->uk_task_ptr = uk_task_ptr;
|
||||
#else
|
||||
ARG_UNUSED(uk_task_ptr);
|
||||
#endif
|
||||
|
||||
/*
|
||||
* intlock_key is constructed based on ARCv2 ISA Programmer's
|
||||
* Reference Manual CLRI instruction description:
|
||||
|
|
|
@ -100,7 +100,8 @@ static ALWAYS_INLINE void _thread_monitor_init(struct tcs *tcs /* thread */
|
|||
* @return N/A
|
||||
*/
|
||||
|
||||
void _new_thread(char *pStackMem, unsigned stackSize, _thread_entry_t pEntry,
|
||||
void _new_thread(char *pStackMem, unsigned stackSize,
|
||||
void *uk_task_ptr, _thread_entry_t pEntry,
|
||||
void *parameter1, void *parameter2, void *parameter3,
|
||||
int priority, unsigned options)
|
||||
{
|
||||
|
@ -143,6 +144,12 @@ void _new_thread(char *pStackMem, unsigned stackSize, _thread_entry_t pEntry,
|
|||
tcs->entry = (struct __thread_entry *)(pInitCtx);
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_MICROKERNEL
|
||||
tcs->uk_task_ptr = uk_task_ptr;
|
||||
#else
|
||||
ARG_UNUSED(uk_task_ptr);
|
||||
#endif
|
||||
|
||||
tcs->preempReg.psp = (uint32_t)pInitCtx;
|
||||
tcs->basepri = 0;
|
||||
|
||||
|
|
|
@ -64,7 +64,7 @@ void _thread_entry_wrapper(_thread_entry_t, _thread_arg_t,
|
|||
* @return N/A
|
||||
*/
|
||||
static void _new_thread_internal(char *pStackMem, unsigned stackSize,
|
||||
int priority, unsigned options)
|
||||
void *uk_task_ptr, int priority, unsigned options)
|
||||
{
|
||||
unsigned long *pInitialCtx;
|
||||
/* ptr to the new task's tcs */
|
||||
|
@ -92,6 +92,11 @@ static void _new_thread_internal(char *pStackMem, unsigned stackSize,
|
|||
tcs->custom_data = NULL;
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_MICROKERNEL
|
||||
tcs->uk_task_ptr = uk_task_ptr;
|
||||
#else
|
||||
ARG_UNUSED(uk_task_ptr);
|
||||
#endif
|
||||
|
||||
/*
|
||||
* The creation of the initial stack for the task has already been done.
|
||||
|
@ -287,7 +292,8 @@ __asm__("\t.globl _thread_entry\n"
|
|||
*
|
||||
* @return opaque pointer to initialized TCS structure
|
||||
*/
|
||||
void _new_thread(char *pStackMem, unsigned stackSize, _thread_entry_t pEntry,
|
||||
void _new_thread(char *pStackMem, unsigned stackSize,
|
||||
void *uk_task_ptr, _thread_entry_t pEntry,
|
||||
void *parameter1, void *parameter2, void *parameter3,
|
||||
int priority, unsigned options)
|
||||
{
|
||||
|
@ -347,5 +353,5 @@ void _new_thread(char *pStackMem, unsigned stackSize, _thread_entry_t pEntry,
|
|||
* is located at the "low end" of memory set aside for the thread's stack.
|
||||
*/
|
||||
|
||||
_new_thread_internal(pStackMem, stackSize, priority, options);
|
||||
_new_thread_internal(pStackMem, stackSize, uk_task_ptr, priority, options);
|
||||
}
|
||||
|
|
|
@ -60,9 +60,9 @@ void _thread_entry_wrapper(_thread_entry_t, _thread_arg_t,
|
|||
*/
|
||||
|
||||
void _new_thread(char *stack_memory, unsigned stack_size,
|
||||
_thread_entry_t thread_func, void *parameter1,
|
||||
void *parameter2, void *parameter3, int priority,
|
||||
unsigned options)
|
||||
void *uk_task_ptr, _thread_entry_t thread_func,
|
||||
void *parameter1, void *parameter2, void *parameter3,
|
||||
int priority, unsigned options)
|
||||
{
|
||||
unsigned long *thread_context;
|
||||
struct tcs *tcs = (struct tcs *)stack_memory;
|
||||
|
@ -118,6 +118,11 @@ void _new_thread(char *stack_memory, unsigned stack_size,
|
|||
*thread_context = (unsigned long)(thread_context + 4);
|
||||
*--thread_context = 0;
|
||||
|
||||
#ifdef CONFIG_MICROKERNEL
|
||||
tcs->uk_task_ptr = uk_task_ptr;
|
||||
#else
|
||||
ARG_UNUSED(uk_task_ptr);
|
||||
#endif
|
||||
tcs->coopReg.esp = (unsigned long)thread_context;
|
||||
#if defined(CONFIG_THREAD_MONITOR)
|
||||
{
|
||||
|
|
|
@ -206,6 +206,7 @@ static void start_task(struct k_task *X, void (*func)(void))
|
|||
|
||||
_new_thread((char *)X->workspace, /* pStackMem */
|
||||
X->worksize, /* stackSize */
|
||||
X, /* microkernel task pointer */
|
||||
(_thread_entry_t)func, /* pEntry */
|
||||
parameter1, /* parameter1 */
|
||||
(void *)0, /* parameter2 */
|
||||
|
|
|
@ -48,8 +48,9 @@ extern void _thread_entry(_thread_entry_t,
|
|||
_thread_arg_t);
|
||||
|
||||
extern void _new_thread(char *pStack, unsigned stackSize,
|
||||
_thread_entry_t pEntry, _thread_arg_t arg1,
|
||||
_thread_arg_t arg2, _thread_arg_t arg3,
|
||||
void *uk_task_ptr, _thread_entry_t pEntry,
|
||||
_thread_arg_t arg1, _thread_arg_t arg2,
|
||||
_thread_arg_t arg3,
|
||||
int prio, unsigned options);
|
||||
|
||||
/* context switching and scheduling-related routines */
|
||||
|
|
|
@ -81,6 +81,7 @@ nano_thread_id_t _fiber_start(char *pStack,
|
|||
tcs = (struct tcs *) pStack;
|
||||
_new_thread(pStack,
|
||||
stackSize,
|
||||
NULL,
|
||||
(_thread_entry_t)pEntry,
|
||||
(void *)parameter1,
|
||||
(void *)parameter2,
|
||||
|
@ -193,7 +194,7 @@ nano_thread_id_t fiber_delayed_start(char *stack,
|
|||
struct tcs *tcs;
|
||||
|
||||
tcs = (struct tcs *)stack;
|
||||
_new_thread(stack, stack_size_in_bytes, (_thread_entry_t)entry_point,
|
||||
_new_thread(stack, stack_size_in_bytes, NULL, (_thread_entry_t)entry_point,
|
||||
(void *)param1, (void *)param2, (void *)0, priority, options);
|
||||
|
||||
key = irq_lock();
|
||||
|
|
|
@ -93,6 +93,9 @@ char __noinit _interrupt_stack[CONFIG_ISR_STACK_SIZE];
|
|||
#endif
|
||||
|
||||
#ifdef CONFIG_NANOKERNEL
|
||||
|
||||
#define MICROKERNEL_IDLE_TASK_PTR (NULL)
|
||||
|
||||
/**
|
||||
*
|
||||
* @brief Mainline for nanokernel's background task
|
||||
|
@ -120,6 +123,13 @@ static void _main(void)
|
|||
main();
|
||||
}
|
||||
#else
|
||||
|
||||
typedef int32_t ktask_t; /* Must match definition in base_api.h */
|
||||
|
||||
extern ktask_t _k_task_ptr_idle;
|
||||
|
||||
#define MICROKERNEL_IDLE_TASK_PTR ((void *) _k_task_ptr_idle)
|
||||
|
||||
/* microkernel has its own implementation of _main() */
|
||||
|
||||
extern void _main(void);
|
||||
|
@ -178,6 +188,7 @@ static void nano_init(struct tcs *dummyOutContext)
|
|||
|
||||
_new_thread(main_task_stack, /* pStackMem */
|
||||
CONFIG_MAIN_STACK_SIZE, /* stackSize */
|
||||
MICROKERNEL_IDLE_TASK_PTR, /* ptr to idle task */
|
||||
(_thread_entry_t)_main, /* pEntry */
|
||||
(_thread_arg_t)0, /* parameter1 */
|
||||
(_thread_arg_t)0, /* parameter2 */
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue