mirror of https://github.com/rusefi/ChibiOS.git
New OS instances module, architectural cleanup.
git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@14232 27425a3e-05d8-49a3-a47f-9c15f0e5edd8
This commit is contained in:
parent
2ca81e8169
commit
d9b773679c
|
@ -56,7 +56,7 @@ void c1_main(void) {
|
|||
* system initialization on the other side.
|
||||
*/
|
||||
chSysWaitSystemState(ch_sys_running);
|
||||
chSchObjectInit(&ch1, &ch_core1_cfg);
|
||||
chInstanceObjectInit(&ch1, &ch_core1_cfg);
|
||||
|
||||
/* It is alive now.*/
|
||||
chSysUnlock();
|
||||
|
|
|
@ -52,6 +52,7 @@
|
|||
*
|
||||
* package OS {
|
||||
* class "Port Layer" <<(S,#FF7700) Singleton>> {
|
||||
* + {static} port_init()
|
||||
* + {static} port_lock()
|
||||
* + {static} port_unlock()
|
||||
* + {static} port_suspend()
|
||||
|
@ -151,28 +152,32 @@
|
|||
* ready_list_t "1" --* os_instance_t : instance\nready list
|
||||
*
|
||||
* package "Virtual Timers" {
|
||||
* class virtual_timer_header_t {
|
||||
* # next : virtual_timer_header_t *
|
||||
* # prev : virtual_timer_header_t *
|
||||
* # delta: sysinterval_t
|
||||
* class delta_list_t {
|
||||
* - next : delta_list_t *
|
||||
* - prev : delta_list_t *
|
||||
* - delta : sysinterval_t
|
||||
* }
|
||||
* class virtual_timer_t {
|
||||
* # func : vtfunc_t
|
||||
* # par : void *
|
||||
* - dlist : delta_list_t
|
||||
* - func : vtfunc_t
|
||||
* - par : void *
|
||||
* + chVTObjectInit()
|
||||
* + chVTSet()
|
||||
* + chVTReset()
|
||||
* }
|
||||
* class virtual_timers_list_t {
|
||||
* # systime : systime_t
|
||||
* # lasttime : systime_t
|
||||
* - dlist : delta_list_t
|
||||
* - systime : systime_t
|
||||
* - lasttime : systime_t
|
||||
* - laststamp : uint64_t
|
||||
* # __vt_init()
|
||||
* }
|
||||
* }
|
||||
*
|
||||
* "Virtual Timers" <..> OS : use
|
||||
* virtual_timer_header_t <|-- virtual_timer_t
|
||||
* virtual_timer_header_t <|-- virtual_timers_list_t
|
||||
* virtual_timer_t *-- "1" delta_list_t
|
||||
* virtual_timers_list_t o-- "0..*" virtual_timer_t : active timers
|
||||
* virtual_timers_list_t *-- "1" delta_list_t
|
||||
*
|
||||
* @enduml
|
||||
*
|
||||
|
|
|
@ -110,6 +110,7 @@
|
|||
#include "chsys.h"
|
||||
#include "chvt.h"
|
||||
#include "chschd.h"
|
||||
#include "chinstances.h"
|
||||
#include "chthreads.h"
|
||||
|
||||
/* Optional subsystems headers.*/
|
||||
|
|
|
@ -0,0 +1,73 @@
|
|||
/*
|
||||
ChibiOS - Copyright (C) 2006,2007,2008,2009,2010,2011,2012,2013,2014,
|
||||
2015,2016,2017,2018,2019,2020,2021 Giovanni Di Sirio.
|
||||
|
||||
This file is part of ChibiOS.
|
||||
|
||||
ChibiOS is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation version 3 of the License.
|
||||
|
||||
ChibiOS is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file rt/include/chinstances.h
|
||||
* @brief OS instances macros and structures.
|
||||
*
|
||||
* @addtogroup instances
|
||||
* @{
|
||||
*/
|
||||
|
||||
#ifndef CHINSTANCES_H
|
||||
#define CHINSTANCES_H
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module constants. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module pre-compile time settings. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Derived constants and error checks. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module data structures and types. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module macros. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*===========================================================================*/
|
||||
/* External declarations. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*
|
||||
* Scheduler APIs.
|
||||
*/
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
void chInstanceObjectInit(os_instance_t *oip,
|
||||
const os_instance_config_t *oicp);
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module inline functions. */
|
||||
/*===========================================================================*/
|
||||
|
||||
#endif /* CHINSTANCES_H */
|
||||
|
||||
/** @} */
|
|
@ -18,6 +18,7 @@ KERNSRC := $(CHIBIOS)/os/rt/src/chsys.c \
|
|||
$(CHIBIOS)/os/rt/src/chtrace.c \
|
||||
$(CHIBIOS)/os/rt/src/chvt.c \
|
||||
$(CHIBIOS)/os/rt/src/chschd.c \
|
||||
$(CHIBIOS)/os/rt/src/chinstances.c \
|
||||
$(CHIBIOS)/os/rt/src/chthreads.c
|
||||
ifneq ($(findstring CH_CFG_USE_TM TRUE,$(CHCONF)),)
|
||||
KERNSRC += $(CHIBIOS)/os/rt/src/chtm.c
|
||||
|
|
|
@ -0,0 +1,179 @@
|
|||
/*
|
||||
ChibiOS - Copyright (C) 2006,2007,2008,2009,2010,2011,2012,2013,2014,
|
||||
2015,2016,2017,2018,2019,2020,2021 Giovanni Di Sirio.
|
||||
|
||||
This file is part of ChibiOS.
|
||||
|
||||
ChibiOS is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation version 3 of the License.
|
||||
|
||||
ChibiOS is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file rt/src/chinstance.c
|
||||
* @brief OS instances code.
|
||||
*
|
||||
* @addtogroup instances
|
||||
* @details OS instances management.
|
||||
* @{
|
||||
*/
|
||||
|
||||
#include "ch.h"
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module local definitions. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module exported variables. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module local types. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module local variables. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module local functions. */
|
||||
/*===========================================================================*/
|
||||
|
||||
#if (CH_CFG_NO_IDLE_THREAD == FALSE) || defined(__DOXYGEN__)
|
||||
/**
|
||||
* @brief This function implements the idle thread infinite loop.
|
||||
* @details The function puts the processor in the lowest power mode capable
|
||||
* to serve interrupts.<br>
|
||||
* The priority is internally set to the minimum system value so
|
||||
* that this thread is executed only if there are no other ready
|
||||
* threads in the system.
|
||||
*
|
||||
* @param[in] p the thread parameter, unused in this scenario
|
||||
*/
|
||||
static void __idle_thread(void *p) {
|
||||
|
||||
(void)p;
|
||||
|
||||
while (true) {
|
||||
/*lint -save -e522 [2.2] Apparently no side effects because it contains
|
||||
an asm instruction.*/
|
||||
port_wait_for_interrupt();
|
||||
/*lint -restore*/
|
||||
CH_CFG_IDLE_LOOP_HOOK();
|
||||
}
|
||||
}
|
||||
#endif /* CH_CFG_NO_IDLE_THREAD == FALSE */
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Module exported functions. */
|
||||
/*===========================================================================*/
|
||||
|
||||
/**
|
||||
* @brief Initializes a system instance.
|
||||
* @note The system instance is in I-Lock state after initialization.
|
||||
*
|
||||
* @param[out] oip pointer to the @p os_instance_t structure
|
||||
* @param[in] oicp pointer to the @p os_instance_config_t structure
|
||||
*
|
||||
* @special
|
||||
*/
|
||||
void chInstanceObjectInit(os_instance_t *oip,
|
||||
const os_instance_config_t *oicp) {
|
||||
core_id_t core_id;
|
||||
|
||||
/* Registering into the global system structure.*/
|
||||
#if CH_CFG_SMP_MODE == TRUE
|
||||
core_id = port_get_core_id();
|
||||
#else
|
||||
core_id = 0U;
|
||||
#endif
|
||||
chDbgAssert(ch_system.instances[core_id] == NULL, "instance already registered");
|
||||
ch_system.instances[core_id] = oip;
|
||||
|
||||
/* Core associated to this instance.*/
|
||||
oip->core_id = core_id;
|
||||
|
||||
/* Keeping a reference to the configuration data.*/
|
||||
oip->config = oicp;
|
||||
|
||||
/* Port initialization for the current instance.*/
|
||||
port_init(oip);
|
||||
|
||||
/* Ready list initialization.*/
|
||||
ch_pqueue_init(&oip->rlist.pqueue);
|
||||
|
||||
#if (CH_CFG_USE_REGISTRY == TRUE) && (CH_CFG_SMP_MODE == FALSE)
|
||||
/* Registry initialization when SMP mode is disabled.*/
|
||||
ch_queue_init(&oip->reglist);
|
||||
#endif
|
||||
|
||||
/* Virtual timers list initialization.*/
|
||||
__vt_object_init(&oip->vtlist);
|
||||
|
||||
/* Debug support initialization.*/
|
||||
__dbg_object_init(&oip->dbg);
|
||||
|
||||
#if CH_DBG_TRACE_MASK != CH_DBG_TRACE_MASK_DISABLED
|
||||
/* Trace buffer initialization.*/
|
||||
__trace_init(oip);
|
||||
#endif
|
||||
|
||||
/* Statistics initialization.*/
|
||||
#if CH_DBG_STATISTICS == TRUE
|
||||
__stats_object_init(&oip->kernel_stats);
|
||||
#endif
|
||||
|
||||
#if CH_CFG_NO_IDLE_THREAD == FALSE
|
||||
/* Now this instructions flow becomes the main thread.*/
|
||||
#if CH_CFG_USE_REGISTRY == TRUE
|
||||
oip->rlist.current = __thd_object_init(oip, &oip->mainthread,
|
||||
(const char *)&ch_debug, NORMALPRIO);
|
||||
#else
|
||||
oip->rlist.current = __thd_object_init(oip, &oip->mainthread,
|
||||
"main", NORMALPRIO);
|
||||
#endif
|
||||
#else
|
||||
/* Now this instructions flow becomes the idle thread.*/
|
||||
oip->rlist.current = __thd_object_init(oip, &oip->mainthread,
|
||||
"idle", IDLEPRIO);
|
||||
#endif
|
||||
|
||||
#if (CH_DBG_ENABLE_STACK_CHECK == TRUE) || (CH_CFG_USE_DYNAMIC == TRUE)
|
||||
oip->rlist.current->wabase = oicp->mainthread_base;
|
||||
#endif
|
||||
|
||||
/* Setting up the caller as current thread.*/
|
||||
oip->rlist.current->state = CH_STATE_CURRENT;
|
||||
|
||||
/* User instance initialization hook.*/
|
||||
CH_CFG_OS_INSTANCE_INIT_HOOK(oip);
|
||||
|
||||
#if CH_CFG_NO_IDLE_THREAD == FALSE
|
||||
{
|
||||
thread_descriptor_t idle_descriptor = {
|
||||
.name = "idle",
|
||||
.wbase = oicp->idlethread_base,
|
||||
.wend = oicp->idlethread_end,
|
||||
.prio = IDLEPRIO,
|
||||
.funcp = __idle_thread,
|
||||
.arg = NULL
|
||||
};
|
||||
|
||||
/* This thread has the lowest priority in the system, its role is just to
|
||||
serve interrupts in its context while keeping the lowest energy saving
|
||||
mode compatible with the system status.*/
|
||||
(void) chThdCreateI(&idle_descriptor);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
/** @} */
|
|
@ -48,31 +48,6 @@
|
|||
/* Module local functions. */
|
||||
/*===========================================================================*/
|
||||
|
||||
#if (CH_CFG_NO_IDLE_THREAD == FALSE) || defined(__DOXYGEN__)
|
||||
/**
|
||||
* @brief This function implements the idle thread infinite loop.
|
||||
* @details The function puts the processor in the lowest power mode capable
|
||||
* to serve interrupts.<br>
|
||||
* The priority is internally set to the minimum system value so
|
||||
* that this thread is executed only if there are no other ready
|
||||
* threads in the system.
|
||||
*
|
||||
* @param[in] p the thread parameter, unused in this scenario
|
||||
*/
|
||||
static void __idle_thread(void *p) {
|
||||
|
||||
(void)p;
|
||||
|
||||
while (true) {
|
||||
/*lint -save -e522 [2.2] Apparently no side effects because it contains
|
||||
an asm instruction.*/
|
||||
port_wait_for_interrupt();
|
||||
/*lint -restore*/
|
||||
CH_CFG_IDLE_LOOP_HOOK();
|
||||
}
|
||||
}
|
||||
#endif /* CH_CFG_NO_IDLE_THREAD == FALSE */
|
||||
|
||||
/**
|
||||
* @brief Inserts a thread in the Ready List placing it behind its peers.
|
||||
* @details The thread is positioned behind all threads with higher or equal
|
||||
|
@ -284,105 +259,6 @@ void ch_sch_prio_insert(ch_queue_t *tp, ch_queue_t *qp) {
|
|||
}
|
||||
#endif /* CH_CFG_OPTIMIZE_SPEED */
|
||||
|
||||
/**
|
||||
* @brief Initializes a system instance.
|
||||
* @note The system instance is in I-Lock state after initialization.
|
||||
*
|
||||
* @param[out] oip pointer to the @p os_instance_t structure
|
||||
* @param[in] oicp pointer to the @p os_instance_config_t structure
|
||||
*
|
||||
* @special
|
||||
*/
|
||||
void chSchObjectInit(os_instance_t *oip,
|
||||
const os_instance_config_t *oicp) {
|
||||
core_id_t core_id;
|
||||
|
||||
/* Registering into the global system structure.*/
|
||||
#if CH_CFG_SMP_MODE == TRUE
|
||||
core_id = port_get_core_id();
|
||||
#else
|
||||
core_id = 0U;
|
||||
#endif
|
||||
chDbgAssert(ch_system.instances[core_id] == NULL, "instance already registered");
|
||||
ch_system.instances[core_id] = oip;
|
||||
|
||||
/* Core associated to this instance.*/
|
||||
oip->core_id = core_id;
|
||||
|
||||
/* Keeping a reference to the configuration data.*/
|
||||
oip->config = oicp;
|
||||
|
||||
/* Port initialization for the current instance.*/
|
||||
port_init(oip);
|
||||
|
||||
/* Ready list initialization.*/
|
||||
ch_pqueue_init(&oip->rlist.pqueue);
|
||||
|
||||
#if (CH_CFG_USE_REGISTRY == TRUE) && (CH_CFG_SMP_MODE == FALSE)
|
||||
/* Registry initialization when SMP mode is disabled.*/
|
||||
ch_queue_init(&oip->reglist);
|
||||
#endif
|
||||
|
||||
/* Virtual timers list initialization.*/
|
||||
__vt_object_init(&oip->vtlist);
|
||||
|
||||
/* Debug support initialization.*/
|
||||
__dbg_object_init(&oip->dbg);
|
||||
|
||||
#if CH_DBG_TRACE_MASK != CH_DBG_TRACE_MASK_DISABLED
|
||||
/* Trace buffer initialization.*/
|
||||
__trace_init(oip);
|
||||
#endif
|
||||
|
||||
/* Statistics initialization.*/
|
||||
#if CH_DBG_STATISTICS == TRUE
|
||||
__stats_object_init(&oip->kernel_stats);
|
||||
#endif
|
||||
|
||||
#if CH_CFG_NO_IDLE_THREAD == FALSE
|
||||
/* Now this instructions flow becomes the main thread.*/
|
||||
#if CH_CFG_USE_REGISTRY == TRUE
|
||||
oip->rlist.current = __thd_object_init(oip, &oip->mainthread,
|
||||
(const char *)&ch_debug, NORMALPRIO);
|
||||
#else
|
||||
oip->rlist.current = __thd_object_init(oip, &oip->mainthread,
|
||||
"main", NORMALPRIO);
|
||||
#endif
|
||||
#else
|
||||
/* Now this instructions flow becomes the idle thread.*/
|
||||
oip->rlist.current = __thd_object_init(oip, &oip->mainthread,
|
||||
"idle", IDLEPRIO);
|
||||
#endif
|
||||
|
||||
#if (CH_DBG_ENABLE_STACK_CHECK == TRUE) || (CH_CFG_USE_DYNAMIC == TRUE)
|
||||
oip->rlist.current->wabase = oicp->mainthread_base;
|
||||
#endif
|
||||
|
||||
/* Setting up the caller as current thread.*/
|
||||
oip->rlist.current->state = CH_STATE_CURRENT;
|
||||
|
||||
/* User instance initialization hook.*/
|
||||
CH_CFG_OS_INSTANCE_INIT_HOOK(oip);
|
||||
|
||||
#if CH_CFG_NO_IDLE_THREAD == FALSE
|
||||
{
|
||||
thread_descriptor_t idle_descriptor = {
|
||||
.name = "idle",
|
||||
.wbase = oicp->idlethread_base,
|
||||
.wend = oicp->idlethread_end,
|
||||
.prio = IDLEPRIO,
|
||||
.funcp = __idle_thread,
|
||||
.arg = NULL
|
||||
};
|
||||
|
||||
/* This thread has the lowest priority in the system, its role is just to
|
||||
serve interrupts in its context while keeping the lowest energy saving
|
||||
mode compatible with the system status.*/
|
||||
(void) chThdCreateI(&idle_descriptor);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Inserts a thread in the Ready List placing it behind its peers.
|
||||
* @details The thread is positioned behind all threads with higher or equal
|
||||
|
|
|
@ -180,7 +180,7 @@ void chSysInit(void) {
|
|||
__oslib_init();
|
||||
|
||||
/* Initializing default OS instance.*/
|
||||
chSchObjectInit(&ch0, &ch_core0_cfg);
|
||||
chInstanceObjectInit(&ch0, &ch_core0_cfg);
|
||||
|
||||
/* It is alive now.*/
|
||||
ch_system.state = ch_sys_running;
|
||||
|
|
Loading…
Reference in New Issue