diff --git a/components/drivers/ipc/SConscript b/components/drivers/ipc/SConscript index 892701733c5..51215156ae3 100644 --- a/components/drivers/ipc/SConscript +++ b/components/drivers/ipc/SConscript @@ -13,7 +13,7 @@ if not GetDepend('RT_USING_SMP'): else: SrcRemove(src, 'completion_up.c') -group = DefineGroup('DeviceDrivers', src, depend = ['RT_USING_DEVICE_IPC'], CPPPATH = CPPPATH, LOCAL_CPPDEFINES=['__RT_IPC_SOURCE__']) +group = DefineGroup('DeviceDrivers', src, depend = ['RT_USING_DEVICE_IPC'], CPPPATH = CPPPATH) list = os.listdir(cwd) for item in list: diff --git a/components/finsh/cmd.c b/components/finsh/cmd.c index a9b6979e53d..66f42f9a0a9 100644 --- a/components/finsh/cmd.c +++ b/components/finsh/cmd.c @@ -221,7 +221,9 @@ long list_thread(void) rt_list_t *next = (rt_list_t *)RT_NULL; const char *item_title = "thread"; const size_t tcb_strlen = sizeof(void *) * 2 + 2; +#ifdef RT_USING_CPU_USAGE_TRACER const size_t usage_strlen = sizeof(void *) + 1; +#endif int maxlen; list_find_init(&find_arg, RT_Object_Class_Thread, obj_list, sizeof(obj_list) / sizeof(obj_list[0])); @@ -230,22 +232,40 @@ long list_thread(void) maxlen = RT_NAME_MAX; #ifdef RT_USING_SMP - rt_kprintf("%-*.*s cpu bind pri status sp stack size max used left tick error tcb addr usage\n", maxlen, maxlen, item_title); + rt_kprintf("%-*.*s cpu bind pri status sp stack size max used left tick error tcb addr ", maxlen, maxlen, item_title); +#ifdef RT_USING_CPU_USAGE_TRACER + rt_kprintf("usage count last time"); +#endif + rt_kprintf("\n"); object_split(maxlen); - rt_kprintf(" --- ---- --- ------- ---------- ---------- ------ ---------- -------"); - rt_kprintf(" "); + rt_kprintf(" --- ---- --- ------- ---------- ---------- ------ ---------- ------- "); object_split(tcb_strlen); rt_kprintf(" "); +#ifdef RT_USING_CPU_USAGE_TRACER object_split(usage_strlen); + rt_kprintf(" "); + object_split(8); + rt_kprintf(" "); + object_split(10); +#endif rt_kprintf("\n"); #else - rt_kprintf("%-*.*s pri status sp stack size max used left tick error tcb addr usage\n", maxlen, maxlen, item_title); + rt_kprintf("%-*.*s pri status sp stack size max used left tick error tcb addr ", maxlen, maxlen, item_title); +#ifdef RT_USING_CPU_USAGE_TRACER + rt_kputs("usage count last time"); +#endif + rt_kprintf("\n"); object_split(maxlen); - rt_kprintf(" --- ------- ---------- ---------- ------ ---------- -------"); - rt_kprintf(" "); + rt_kprintf(" --- ------- ---------- ---------- ------ ---------- ------- "); object_split(tcb_strlen); rt_kprintf(" "); +#ifdef RT_USING_CPU_USAGE_TRACER object_split(usage_strlen); + rt_kprintf(" "); + object_split(8); + rt_kprintf(" "); + object_split(10); +#endif rt_kprintf("\n"); #endif /*RT_USING_SMP*/ @@ -310,6 +330,11 @@ long list_thread(void) thread->remaining_tick, rt_strerror(thread->error), thread); +#ifdef RT_USING_CPU_USAGE_TRACER + uint16_t usage = rt_thread_get_usage(thread); + rt_kprintf(" %2hu.%1hu%%%8d%10d", usage / 10, usage % 10, thread->ctx_count, thread->ctx_last_time); +#endif + rt_kprintf(" \n"); #else ptr = (rt_uint8_t *)thread->stack_addr; while (*ptr == '#') ptr ++; @@ -323,9 +348,10 @@ long list_thread(void) thread); #endif #ifdef RT_USING_CPU_USAGE_TRACER - rt_kprintf(" %3d%%\n", rt_thread_get_usage(thread)); + uint16_t usage = rt_thread_get_usage(thread); + rt_kprintf(" %2hu.%1hu%%%8d%10d", usage / 10, usage % 10, thread->ctx_count, thread->ctx_last_time); #else - rt_kprintf(" N/A\n"); + rt_kprintf("\n"); #endif } } diff --git a/include/rtdef.h b/include/rtdef.h index 3833f87f2e9..81235b651f8 100644 --- a/include/rtdef.h +++ b/include/rtdef.h @@ -936,7 +936,9 @@ struct rt_thread rt_ubase_t user_time; /**< Ticks on user */ rt_ubase_t system_time; /**< Ticks on system */ rt_ubase_t total_time_prev; /**< Previous total ticks snapshot */ - rt_uint8_t cpu_usage; /**< Recent CPU usage in percent */ + rt_ubase_t cpu_usage; /**< Recent CPU usage in percent */ + rt_ubase_t ctx_last_time; /**< Last context switch time */ + rt_ubase_t ctx_count; /**< Context switch count */ #endif /* RT_USING_CPU_USAGE_TRACER */ #ifdef RT_USING_MEM_PROTECTION diff --git a/include/rtthread.h b/include/rtthread.h index 177ea877831..b1000b9d750 100644 --- a/include/rtthread.h +++ b/include/rtthread.h @@ -170,7 +170,7 @@ void rt_thread_wakeup_set(struct rt_thread *thread, rt_wakeup_func_t func, void* #endif /* RT_USING_SMART */ rt_err_t rt_thread_get_name(rt_thread_t thread, char *name, rt_uint8_t name_size); #ifdef RT_USING_CPU_USAGE_TRACER -rt_uint8_t rt_thread_get_usage(rt_thread_t thread); +rt_uint16_t rt_thread_get_usage(rt_thread_t thread); #endif /* RT_USING_CPU_USAGE_TRACER */ #ifdef RT_USING_SIGNALS void rt_thread_alloc_sig(rt_thread_t tid); diff --git a/src/kservice.c b/src/kservice.c index 02396203d0f..0d70b32e9a3 100644 --- a/src/kservice.c +++ b/src/kservice.c @@ -674,8 +674,12 @@ static void _cpu_usage_refresh_threads(rt_uint64_t total_delta) if (total_delta > 0U) { - rt_uint64_t usage = (thread_delta * 100U) / total_delta; - t->cpu_usage = (rt_uint8_t)(usage > 100U ? 100U : usage); + rt_uint64_t usage = (thread_delta * 1000U) / total_delta; + t->cpu_usage = (rt_uint16_t)(usage > 1000U ? 1000U : usage); + if (t->cpu_usage == 0 && usage > 0) + { + t->cpu_usage = 1U; + } } else { @@ -731,9 +735,9 @@ static void _cpu_usage_update(void) * @note Sampling interval can be tuned with RT_CPU_USAGE_CALC_INTERVAL_MS. * @note If thread is NULL, an assertion will be triggered in debug builds. */ -rt_uint8_t rt_thread_get_usage(rt_thread_t thread) +rt_uint16_t rt_thread_get_usage(rt_thread_t thread) { - rt_uint8_t usage; + rt_uint16_t usage; RT_ASSERT(thread != RT_NULL); diff --git a/src/scheduler_mp.c b/src/scheduler_mp.c index 4bcbafad6dd..7d894d9b76c 100644 --- a/src/scheduler_mp.c +++ b/src/scheduler_mp.c @@ -879,7 +879,10 @@ rt_err_t rt_sched_unlock_n_resched(rt_sched_lock_level_t level) cpu_id, RT_SCHED_PRIV(to_thread).current_priority, RT_NAME_MAX, to_thread->parent.name, to_thread->sp, RT_NAME_MAX, current_thread->parent.name, current_thread->sp); - +#ifdef RT_USING_CPU_USAGE_TRACER + to_thread->ctx_count++; + to_thread->ctx_last_time = rt_tick_get(); +#endif rt_hw_context_switch((rt_ubase_t)¤t_thread->sp, (rt_ubase_t)&to_thread->sp, to_thread); } @@ -980,7 +983,10 @@ void rt_schedule(void) cpu_id, RT_SCHED_PRIV(to_thread).current_priority, RT_NAME_MAX, to_thread->parent.name, to_thread->sp, RT_NAME_MAX, current_thread->parent.name, current_thread->sp); - +#ifdef RT_USING_CPU_USAGE_TRACER + to_thread->ctx_count++; + to_thread->ctx_last_time = rt_tick_get(); +#endif rt_hw_context_switch((rt_ubase_t)¤t_thread->sp, (rt_ubase_t)&to_thread->sp, to_thread); } @@ -1065,7 +1071,10 @@ void rt_scheduler_do_irq_switch(void *context) cpu_id, RT_SCHED_PRIV(to_thread).current_priority, RT_NAME_MAX, to_thread->parent.name, to_thread->sp, RT_NAME_MAX, current_thread->parent.name, current_thread->sp); - +#ifdef RT_USING_CPU_USAGE_TRACER + to_thread->ctx_count++; + to_thread->ctx_last_time = rt_tick_get(); +#endif rt_hw_context_switch_interrupt(context, (rt_ubase_t)¤t_thread->sp, (rt_ubase_t)&to_thread->sp, to_thread); } diff --git a/src/scheduler_up.c b/src/scheduler_up.c index 8560166fd17..624c7875e15 100644 --- a/src/scheduler_up.c +++ b/src/scheduler_up.c @@ -359,10 +359,12 @@ void rt_schedule(void) extern void rt_thread_handle_sig(rt_bool_t clean_state); RT_OBJECT_HOOK_CALL(rt_scheduler_switch_hook, (from_thread)); - +#ifdef RT_USING_CPU_USAGE_TRACER + to_thread->ctx_count++; + to_thread->ctx_last_time = rt_tick_get(); +#endif rt_hw_context_switch((rt_uintptr_t)&from_thread->sp, (rt_uintptr_t)&to_thread->sp); - /* enable interrupt */ rt_hw_interrupt_enable(level); @@ -390,7 +392,10 @@ void rt_schedule(void) else { LOG_D("switch in interrupt"); - +#ifdef RT_USING_CPU_USAGE_TRACER + to_thread->ctx_count++; + to_thread->ctx_last_time = rt_tick_get(); +#endif rt_hw_context_switch_interrupt((rt_uintptr_t)&from_thread->sp, (rt_uintptr_t)&to_thread->sp, from_thread, to_thread); }