From e49e84c9abd9a67d92fd12ab18794ed1d809f70c Mon Sep 17 00:00:00 2001 From: Joel Sherrill Date: Mon, 21 May 2007 20:28:02 +0000 Subject: 2007-05-21 Joel Sherrill * libmisc/Makefile.am, libmisc/cpuuse/README: Split remaining CPU Usage functionality into multiple files to eliminate unnecessary cohesion. Update README. * libmisc/cpuuse/cpuusagereport.c, libmisc/cpuuse/cpuusagereset.c: New files. * libmisc/cpuuse/cpuuse.c: Removed. --- cpukit/ChangeLog | 9 ++ cpukit/libmisc/Makefile.am | 3 +- cpukit/libmisc/cpuuse/README | 15 ++- cpukit/libmisc/cpuuse/cpuusagereport.c | 149 +++++++++++++++++++++++++++++ cpukit/libmisc/cpuuse/cpuusagereset.c | 50 ++++++++++ cpukit/libmisc/cpuuse/cpuuse.c | 169 --------------------------------- 6 files changed, 221 insertions(+), 174 deletions(-) create mode 100644 cpukit/libmisc/cpuuse/cpuusagereport.c create mode 100644 cpukit/libmisc/cpuuse/cpuusagereset.c delete mode 100644 cpukit/libmisc/cpuuse/cpuuse.c diff --git a/cpukit/ChangeLog b/cpukit/ChangeLog index 3da302b705..d8431262b8 100644 --- a/cpukit/ChangeLog +++ b/cpukit/ChangeLog @@ -1,3 +1,12 @@ +2007-05-21 Joel Sherrill + + * libmisc/Makefile.am, libmisc/cpuuse/README: Split remaining CPU Usage + functionality into multiple files to eliminate unnecessary cohesion. + Update README. + * libmisc/cpuuse/cpuusagereport.c, libmisc/cpuuse/cpuusagereset.c: + New files. + * libmisc/cpuuse/cpuuse.c: Removed. + 2007-05-21 Joel Sherrill * rtems/src/ratemonperiod.c: Fix math ordering bug which resulted in a diff --git a/cpukit/libmisc/Makefile.am b/cpukit/libmisc/Makefile.am index afcb6569dc..33ee30182d 100644 --- a/cpukit/libmisc/Makefile.am +++ b/cpukit/libmisc/Makefile.am @@ -19,7 +19,8 @@ libcapture_a_SOURCES = capture/capture.c capture/capture-cli.c \ EXTRA_DIST += cpuuse/README noinst_LIBRARIES += libcpuuse.a -libcpuuse_a_SOURCES = cpuuse/cpuuse.c cpuuse/cpuuse.h +libcpuuse_a_SOURCES = cpuuse/cpuusagereport.c cpuuse/cpuusagereset.c \ + cpuuse/cpuuse.h ## devnull diff --git a/cpukit/libmisc/cpuuse/README b/cpukit/libmisc/cpuuse/README index bd3cc55e34..ac674bb0b6 100644 --- a/cpukit/libmisc/cpuuse/README +++ b/cpukit/libmisc/cpuuse/README @@ -2,13 +2,20 @@ # $Id$ # -This directory contains a CPU usage reported. It provides two -primary features: +This directory contains code to report and reset per-task CPU usage. +If the BSP supports nanosecond timestamp granularity, this this information +is very accurate. Otherwise, it is dependendent on the tick granularity. - + provides an educated guess at each task's CPU usage +It provides two primary features: + + + Generate a CPU Usage Report + + Reset CPU Usage Information NOTES: -1. CPU usage is "docked" by a clock tick at each context switch. +1. If configured for tick granularity, CPU usage is "docked" by a + clock tick at each context switch. +2. If configured for nanosecond granularity, no work is done at each + clock tick. All bookkeeping is done as part of a context switch. diff --git a/cpukit/libmisc/cpuuse/cpuusagereport.c b/cpukit/libmisc/cpuuse/cpuusagereport.c new file mode 100644 index 0000000000..89f264db40 --- /dev/null +++ b/cpukit/libmisc/cpuuse/cpuusagereport.c @@ -0,0 +1,149 @@ +/* + * CPU Usage Reporter + * + * COPYRIGHT (c) 1989-2007 + * On-Line Applications Research Corporation (OAR). + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.com/license/LICENSE. + * + * $Id$ + */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include + +#include +#include +#include +#include +#include + +#include +#include + +#if defined(RTEMS_ENABLE_NANOSECOND_RATE_MONOTONIC_STATISTICS) || \ + defined(RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS) + #include + + /* We print to 1/10's of milliseconds */ + #define NANOSECONDS_DIVIDER 100000 + #define PERCENT_FMT "%04" PRId32 +#endif + +#ifndef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS + uint32_t CPU_usage_Ticks_at_last_reset; +#endif + +/*PAGE + * + * rtems_cpu_usage_report + */ + +void rtems_cpu_usage_report( void ) +{ + uint32_t i; + uint32_t api_index; + Thread_Control *the_thread; + Objects_Information *information; + char name[5]; + uint32_t ival, fval; + #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS + struct timespec uptime; + #else + uint32_t total_units = 0; + #endif + + /* + * When not using nanosecond CPU usage resolution, we have to count + * the number of "ticks" we gave credit for to give the user a rough + * guideline as to what each number means proportionally. + */ + #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS + _TOD_Get_uptime( &uptime ); + #else + for ( api_index = 1 ; api_index <= OBJECTS_APIS_LAST ; api_index++ ) { + if ( !_Objects_Information_table[ api_index ] ) + continue; + information = _Objects_Information_table[ api_index ][ 1 ]; + if ( information ) { + for ( i=1 ; i <= information->maximum ; i++ ) { + the_thread = (Thread_Control *)information->local_table[ i ]; + + if ( the_thread ) + total_units += the_thread->ticks_executed; + } + } + } + #endif + + printk( "CPU Usage by thread\n" + #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS + " ID NAME SECONDS PERCENT\n" + #else + " ID NAME TICKS PERCENT\n" + #endif + ); + + for ( api_index = 1 ; + api_index <= OBJECTS_APIS_LAST ; + api_index++ ) { + if ( !_Objects_Information_table[ api_index ] ) + continue; + information = _Objects_Information_table[ api_index ][ 1 ]; + if ( information ) { + for ( i=1 ; i <= information->maximum ; i++ ) { + the_thread = (Thread_Control *)information->local_table[ i ]; + + if ( !the_thread ) + continue; + + rtems_object_get_name( the_thread->Object.id, sizeof(name), name ); + + printk( "0x%08" PRIx32 " %4s ", the_thread->Object.id, name ); + + #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS + _Timespec_Divide( &the_thread->cpu_time_used, &uptime, &ival, &fval ); + + printk( + "%" PRId32 ".%06d" /* cpu time used */ + " %3" PRId32 ".%02" PRId32 "\n", /* percentage */ + the_thread->cpu_time_used.tv_sec, + the_thread->cpu_time_used.tv_nsec / + TOD_NANOSECONDS_PER_MICROSECOND, + ival, + fval + ); + #else + ival = (total_units) ? + the_thread->ticks_executed * 10000 / total_units : 0; + fval = ival % 100; + ival /= 100; + printk( + "%8" PRId32 " %3" PRId32 ".%02" PRId32"\n", + the_thread->ticks_executed, + ival, + fval + ); + #endif + } + } + } + + #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS + printk( "Uptime %d.%06d seconds\n\n", + uptime.tv_sec, + uptime.tv_nsec / TOD_NANOSECONDS_PER_MICROSECOND + ); + #else + printk( + "Ticks since last reset = %" PRId32 "\n", + _Watchdog_Ticks_since_boot - CPU_usage_Ticks_at_last_reset + ); + printk( "Total Units = %" PRId32 "\n\n", total_units ); + #endif +} diff --git a/cpukit/libmisc/cpuuse/cpuusagereset.c b/cpukit/libmisc/cpuuse/cpuusagereset.c new file mode 100644 index 0000000000..6622b93c90 --- /dev/null +++ b/cpukit/libmisc/cpuuse/cpuusagereset.c @@ -0,0 +1,50 @@ +/* + * CPU Usage Reporter + * + * COPYRIGHT (c) 1989-2007 + * On-Line Applications Research Corporation (OAR). + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.com/license/LICENSE. + * + * $Id$ + */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include + +#include +#include +#include + +#include + +static void CPU_usage_Per_thread_handler( + Thread_Control *the_thread +) +{ + #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS + the_thread->cpu_time_used.tv_sec = 0; + the_thread->cpu_time_used.tv_nsec = 0; + #else + the_thread->ticks_executed = 0; + #endif +} + +/* + * rtems_cpu_usage_reset + */ +void rtems_cpu_usage_reset( void ) +{ + #ifndef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS + extern uint32_t CPU_usage_Ticks_at_last_reset; + + CPU_usage_Ticks_at_last_reset = _Watchdog_Ticks_since_boot; + #endif + + rtems_iterate_over_all_threads(CPU_usage_Per_thread_handler); +} diff --git a/cpukit/libmisc/cpuuse/cpuuse.c b/cpukit/libmisc/cpuuse/cpuuse.c deleted file mode 100644 index cf1b6f2b4d..0000000000 --- a/cpukit/libmisc/cpuuse/cpuuse.c +++ /dev/null @@ -1,169 +0,0 @@ -/* - * CPU Usage Reporter - * - * COPYRIGHT (c) 1989-2007 - * On-Line Applications Research Corporation (OAR). - * - * The license and distribution terms for this file may be - * found in the file LICENSE in this distribution or at - * http://www.rtems.com/license/LICENSE. - * - * $Id$ - */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include - -#include -#include -#include -#include -#include - -#include -#include - -#if defined(RTEMS_ENABLE_NANOSECOND_RATE_MONOTONIC_STATISTICS) || \ - defined(RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS) - #include - - /* We print to 1/10's of milliseconds */ - #define NANOSECONDS_DIVIDER 100000 - #define PERCENT_FMT "%04" PRId32 -#endif - -#ifndef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS - uint32_t CPU_usage_Ticks_at_last_reset; -#endif - -/*PAGE - * - * rtems_cpu_usage_report - */ - -void rtems_cpu_usage_report( void ) -{ - uint32_t i; - uint32_t api_index; - Thread_Control *the_thread; - Objects_Information *information; - char name[5]; - uint32_t ival, fval; - #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS - struct timespec uptime; - #else - uint32_t total_units = 0; - #endif - - /* - * When not using nanosecond CPU usage resolution, we have to count - * the number of "ticks" we gave credit for to give the user a rough - * guideline as to what each number means proportionally. - */ - #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS - _TOD_Get_uptime( &uptime ); - #else - for ( api_index = 1 ; api_index <= OBJECTS_APIS_LAST ; api_index++ ) { - if ( !_Objects_Information_table[ api_index ] ) - continue; - information = _Objects_Information_table[ api_index ][ 1 ]; - if ( information ) { - for ( i=1 ; i <= information->maximum ; i++ ) { - the_thread = (Thread_Control *)information->local_table[ i ]; - - if ( the_thread ) - total_units += the_thread->ticks_executed; - } - } - } - #endif - - printk( "CPU Usage by thread\n" - " ID NAME TICKS PERCENT\n" - ); - - for ( api_index = 1 ; - api_index <= OBJECTS_APIS_LAST ; - api_index++ ) { - if ( !_Objects_Information_table[ api_index ] ) - continue; - information = _Objects_Information_table[ api_index ][ 1 ]; - if ( information ) { - for ( i=1 ; i <= information->maximum ; i++ ) { - the_thread = (Thread_Control *)information->local_table[ i ]; - - if ( !the_thread ) - continue; - - rtems_object_get_name( the_thread->Object.id, sizeof(name), name ); - - printk( "0x%08" PRIx32 " %4s ", the_thread->Object.id, name ); - - #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS - _Timespec_Divide( &the_thread->cpu_time_used, &uptime, &ival, &fval ); - - printk( - "%" PRId32 ".%06d" /* cpu time used */ - " %3" PRId32 ".%02" PRId32 "\n", /* percentage */ - the_thread->cpu_time_used.tv_sec, - the_thread->cpu_time_used.tv_nsec / - TOD_NANOSECONDS_PER_MICROSECOND, - ival, - fval - ); - #else - ival = (total_units) ? - the_thread->ticks_executed * 10000 / total_units : 0; - fval = ival % 100; - ival /= 100; - printk( - "%8" PRId32 " %3" PRId32 ".%02" PRId32"\n", - the_thread->ticks_executed, - ival, - fval - ); - #endif - } - } - } - - #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS - printk( "Uptime %d.%06d seconds\n\n", - uptime.tv_sec, - uptime.tv_nsec / TOD_NANOSECONDS_PER_MICROSECOND - ); - #else - printk( - "Ticks since last reset = %" PRId32 "\n", - _Watchdog_Ticks_since_boot - CPU_usage_Ticks_at_last_reset - ); - printk( "Total Units = %" PRId32 "\n\n", total_units ); - #endif -} - -static void CPU_usage_Per_thread_handler( - Thread_Control *the_thread -) -{ - #ifdef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS - the_thread->cpu_time_used.tv_sec = 0; - the_thread->cpu_time_used.tv_nsec = 0; - #else - the_thread->ticks_executed = 0; - #endif -} - -/* - * rtems_cpu_usage_reset - */ -void rtems_cpu_usage_reset( void ) -{ - #ifndef RTEMS_ENABLE_NANOSECOND_CPU_USAGE_STATISTICS - CPU_usage_Ticks_at_last_reset = _Watchdog_Ticks_since_boot; - #endif - - rtems_iterate_over_all_threads(CPU_usage_Per_thread_handler); -} -- cgit v1.2.3