diff --git a/include/rtthread.h b/include/rtthread.h index c7f35d163..6ab1ed906 100644 --- a/include/rtthread.h +++ b/include/rtthread.h @@ -26,6 +26,7 @@ * 2007-03-03 Bernard clean up the definitions to rtdef.h * 2010-04-11 yi.qiu add module feature * 2013-06-24 Bernard add rt_kprintf re-define when not use RT_USING_CONSOLE. + * 2016-08-09 ArdaFu add new thread and interrupt hook. */ #ifndef __RT_THREAD_H__ @@ -153,6 +154,11 @@ rt_err_t rt_thread_suspend(rt_thread_t thread); rt_err_t rt_thread_resume(rt_thread_t thread); void rt_thread_timeout(void *parameter); +#ifdef RT_USING_HOOK +void rt_thread_suspend_sethook(void (*hook)(rt_thread_t thread)); +void rt_thread_resume_sethook(void (*hook)(rt_thread_t thread)); +#endif + /* * idle thread interface */ @@ -161,6 +167,7 @@ void rt_thread_idle_init(void); void rt_thread_idle_sethook(void (*hook)(void)); #endif void rt_thread_idle_excute(void); +rt_thread_t rt_thread_idle_gethandler(void); /* * schedule service @@ -460,6 +467,11 @@ void rt_interrupt_leave(void); */ rt_uint8_t rt_interrupt_get_nest(void); +#ifdef RT_USING_HOOK +void rt_interrupt_enter_sethook(void (*hook)(void)); +void rt_interrupt_leave_sethook(void (*hook)(void)); +#endif + #ifdef RT_USING_COMPONENTS_INIT void rt_components_init(void); void rt_components_board_init(void); diff --git a/src/idle.c b/src/idle.c index 867af8761..aab09cb91 100644 --- a/src/idle.c +++ b/src/idle.c @@ -24,6 +24,7 @@ * 2012-12-29 Bernard fix compiling warning. * 2013-12-21 Grissiom let rt_thread_idle_excute loop until there is no * dead thread. + * 2016-08-09 ArdaFu add method to get the handler of the idle thread. */ #include @@ -178,11 +179,7 @@ static void rt_thread_idle_entry(void *parameter) { while (1) { - #ifdef RT_USING_HOOK - if (rt_thread_idle_hook != RT_NULL) - rt_thread_idle_hook(); - #endif - + RT_OBJECT_HOOK_CALL(rt_thread_idle_hook,()); rt_thread_idle_excute(); } } @@ -209,3 +206,14 @@ void rt_thread_idle_init(void) /* startup */ rt_thread_startup(&idle); } + +/** + * @ingroup Thread + * + * This function will get the handler of the idle thread. + * + */ +rt_thread_t rt_thread_idle_gethandler(void) +{ + return (rt_thread_t)(&idle); +} diff --git a/src/irq.c b/src/irq.c index 70b18e018..ca221cf10 100644 --- a/src/irq.c +++ b/src/irq.c @@ -21,11 +21,39 @@ * Date Author Notes * 2006-02-24 Bernard first version * 2006-05-03 Bernard add IRQ_DEBUG + * 2016-08-09 ArdaFu add interrupt enter and leave hook. */ #include #include +#ifdef RT_USING_HOOK + +static void (*rt_interrupt_enter_hook)(void); +static void (*rt_interrupt_leave_hook)(void); + +/** + * @ingroup Hook + * This function set a hook function when the system enter a interrupt + * + * @note the hook function must be simple and never be blocked or suspend. + */ +void rt_interrupt_enter_sethook(void (*hook)(void)) +{ + rt_interrupt_enter_hook = hook; +} +/** + * @ingroup Hook + * This function set a hook function when the system exit a interrupt. + * + * @note the hook function must be simple and never be blocked or suspend. + */ +void rt_interrupt_leave_sethook(void (*hook)(void)) +{ + rt_interrupt_leave_hook = hook; +} +#endif + /* #define IRQ_DEBUG */ /** @@ -52,6 +80,7 @@ void rt_interrupt_enter(void) level = rt_hw_interrupt_disable(); rt_interrupt_nest ++; + RT_OBJECT_HOOK_CALL(rt_interrupt_enter_hook,()); rt_hw_interrupt_enable(level); } RTM_EXPORT(rt_interrupt_enter); @@ -72,6 +101,7 @@ void rt_interrupt_leave(void) level = rt_hw_interrupt_disable(); rt_interrupt_nest --; + RT_OBJECT_HOOK_CALL(rt_interrupt_leave_hook,()); rt_hw_interrupt_enable(level); } RTM_EXPORT(rt_interrupt_leave); diff --git a/src/thread.c b/src/thread.c index 487c005b6..b8b582d5b 100644 --- a/src/thread.c +++ b/src/thread.c @@ -35,6 +35,7 @@ * thread preempted, which reported by Jiaxing Lee. * 2011-09-08 Bernard fixed the scheduling issue in rt_thread_startup. * 2012-12-29 Bernard fixed compiling warning. + * 2016-08-09 ArdaFu add thread suspend and resume hook. */ #include @@ -44,6 +45,36 @@ extern rt_list_t rt_thread_priority_table[RT_THREAD_PRIORITY_MAX]; extern struct rt_thread *rt_current_thread; extern rt_list_t rt_thread_defunct; +#ifdef RT_USING_HOOK + +static void (*rt_thread_suspend_hook)(rt_thread_t thread); +static void (*rt_thread_resume_hook)(rt_thread_t thread); +/** + * @ingroup Hook + * This function sets a hook function when the system suspend a thread. + * + * @param hook the specified hook function + * + * @note the hook function must be simple and never be blocked or suspend. + */ +void rt_thread_suspend_sethook(void (*hook)(rt_thread_t thread)) +{ + rt_thread_suspend_hook = hook; +} +/** + * @ingroup Hook + * This function sets a hook function when the system resume a thread. + * + * @param hook the specified hook function + * + * @note the hook function must be simple and never be blocked or suspend. + */ +void rt_thread_resume_sethook(void (*hook)(rt_thread_t thread)) +{ + rt_thread_resume_hook = hook; +} +#endif + void rt_thread_exit(void) { struct rt_thread *thread; @@ -581,6 +612,7 @@ rt_err_t rt_thread_suspend(rt_thread_t thread) /* enable interrupt */ rt_hw_interrupt_enable(temp); + RT_OBJECT_HOOK_CALL(rt_thread_suspend_hook,(thread)); return RT_EOK; } RTM_EXPORT(rt_thread_suspend); @@ -623,6 +655,7 @@ rt_err_t rt_thread_resume(rt_thread_t thread) /* insert to schedule ready list */ rt_schedule_insert_thread(thread); + RT_OBJECT_HOOK_CALL(rt_thread_resume_hook,(thread)); return RT_EOK; } RTM_EXPORT(rt_thread_resume);