OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [rtos/] [ecos-2.0/] [packages/] [services/] [cpuload/] [v2_0/] [src/] [cpuload.cxx] - Blame information for rev 27

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 27 unneback
//==========================================================================
2
//
3
//      cpuload.cxx
4
//
5
//      Estimate the current CPU load.
6
//
7
//==========================================================================
8
//####ECOSGPLCOPYRIGHTBEGIN####
9
// -------------------------------------------
10
// This file is part of eCos, the Embedded Configurable Operating System.
11
// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
12
// Copyright (C) 2002 Gary Thomas
13
//
14
// eCos is free software; you can redistribute it and/or modify it under
15
// the terms of the GNU General Public License as published by the Free
16
// Software Foundation; either version 2 or (at your option) any later version.
17
//
18
// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
19
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
20
// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
21
// for more details.
22
//
23
// You should have received a copy of the GNU General Public License along
24
// with eCos; if not, write to the Free Software Foundation, Inc.,
25
// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
26
//
27
// As a special exception, if other files instantiate templates or use macros
28
// or inline functions from this file, or you compile this file and link it
29
// with other works to produce a work based on this file, this file does not
30
// by itself cause the resulting work to be covered by the GNU General Public
31
// License. However the source code for this file must still be made available
32
// in accordance with section (3) of the GNU General Public License.
33
//
34
// This exception does not invalidate any other reasons why a work based on
35
// this file might be covered by the GNU General Public License.
36
//
37
// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
38
// at http://sources.redhat.com/ecos/ecos-license/
39
// -------------------------------------------
40
//####ECOSGPLCOPYRIGHTEND####
41
//==========================================================================
42
//#####DESCRIPTIONBEGIN####
43
//
44
// Author(s):    Andrew Lunn
45
// Contributors: Andrew Lunn
46
// Date:         2002-08-12
47
// Purpose:      
48
// Description:  
49
//    This provides a simple CPU load meter. All loads are returned
50
//    as a percentage, ie 0-100. This is only a rough measure. Any clever
51
//    power management, sleep modes etc, will cause these results to be
52
//    wrong.
53
//              
54
// This code is part of eCos (tm).
55
//
56
//####DESCRIPTIONEND####
57
//
58
//==========================================================================
59
 
60
#include <cyg/kernel/kapi.h>
61
#include <cyg/hal/hal_arch.h> 
62
#include <cyg/cpuload/cpuload.h>
63
 
64
/* Here we run the idle thread as a high priority thread for 0.1
65
   second.  We see how much the counter in the idle loop is
66
   incremented. This will only work if there are no other threads
67
   running at priority 1 and 2 */
68
 
69
static cyg_thread thread;
70
externC cyg_uint32 idle_thread_loops;
71
char idle_stack[CYGNUM_HAL_STACK_SIZE_MINIMUM];
72
 
73
extern void idle_thread_main( CYG_ADDRESS data );
74
 
75
// -------------------------------------------------------------------------
76
/* We are playing ping-pong with the cpuload_calibrate function and
77
   the idle thread. First cpuload_calibrate runs. Next the idle
78
   thread, then this alarm function and then back to the
79
   cpuload_calibrate function. */
80
 
81
void static
82
alarm_func(cyg_handle_t alarm,cyg_addrword_t data) {
83
  cyg_handle_t idleH = (cyg_handle_t) data;
84
  cyg_thread_suspend(idleH);
85
}
86
 
87
 
88
/* Calibrate the cpuload measurements.*/
89
externC void
90
cyg_cpuload_calibrate(cyg_uint32  *calibration) {
91
  cyg_handle_t counter;
92
  cyg_alarm alarm_s;
93
  cyg_handle_t alarmH;
94
  cyg_uint32 idle_loops_start;
95
  cyg_handle_t idleH;
96
  cyg_priority_t old_priority;
97
 
98
  cyg_thread_create(1,
99
                    idle_thread_main,
100
                    0,
101
                    "Calibration idle thread",
102
                    idle_stack,
103
                    sizeof(idle_stack),
104
                    &idleH,
105
                    &thread);
106
 
107
  cyg_clock_to_counter(cyg_real_time_clock(),&counter);
108
  cyg_alarm_create(counter,alarm_func,(cyg_addrword_t)idleH,&alarmH,&alarm_s);
109
 
110
  cyg_alarm_initialize(alarmH,cyg_current_time()+10,0);
111
  cyg_alarm_enable(alarmH);
112
 
113
  idle_loops_start = idle_thread_loops;
114
 
115
  /* Dont be decieved, remember this is a multithreaded system ! */
116
  old_priority = cyg_thread_get_priority(cyg_thread_self());
117
  cyg_thread_set_priority(cyg_thread_self(),2);
118
  cyg_thread_resume(idleH);
119
  cyg_thread_set_priority(cyg_thread_self(),old_priority);
120
 
121
  *calibration = idle_thread_loops - idle_loops_start;
122
  cyg_alarm_delete(alarmH);
123
  cyg_thread_kill(idleH);
124
  cyg_thread_delete(idleH);
125
}
126
 
127
static void
128
cpuload_alarm_func(cyg_handle_t alarm,cyg_addrword_t data) {
129
  cyg_cpuload_t * cpuload = (cyg_cpuload_t *)data;
130
  cyg_uint32 idle_loops_now = idle_thread_loops;
131
  cyg_uint32 idle_loops;
132
  cyg_uint32 load;
133
 
134
  if (idle_loops_now >= cpuload->last_idle_loops) {
135
    idle_loops = idle_loops_now - cpuload->last_idle_loops;
136
  } else {
137
    idle_loops = ~0 - (cpuload->last_idle_loops - idle_loops_now);
138
  }
139
 
140
  /* We need 64 bit arithmatic to prevent wrap around */
141
  load = (cyg_uint32) (((cyg_uint64) idle_loops * (cyg_uint64)100) /
142
                       (cyg_uint64)cpuload->calibration);
143
  if (load > 100) {
144
    load = 100;
145
  }
146
  load = 100 - load;
147
 
148
  cpuload->average_point1s = load;
149
  cpuload->average_1s = load + ((cpuload->average_1s * 90)/100);
150
  cpuload->average_10s = load + ((cpuload->average_10s * 99)/100);
151
  cpuload->last_idle_loops = idle_loops_now;
152
}
153
 
154
/* Create a CPU load measurements object and start the
155
   measurements. */
156
externC void
157
cyg_cpuload_create(cyg_cpuload_t *cpuload,
158
                   cyg_uint32 calibration,
159
                   cyg_handle_t *handle)
160
{
161
  cyg_handle_t counter;
162
 
163
  cpuload->average_point1s = 0;
164
  cpuload->average_1s = 0;
165
  cpuload->average_10s = 0;
166
  cpuload->calibration = calibration;
167
  cpuload->last_idle_loops = idle_thread_loops;
168
 
169
  cyg_clock_to_counter(cyg_real_time_clock(),&counter);
170
  cyg_alarm_create(counter,
171
                   cpuload_alarm_func,
172
                   (cyg_addrword_t)cpuload,
173
                   &cpuload->alarmH,
174
                   &cpuload->alarm_s);
175
 
176
  cyg_alarm_initialize(cpuload->alarmH,cyg_current_time()+10,10);
177
  cyg_alarm_enable(cpuload->alarmH);
178
 
179
  *handle = (cyg_handle_t) cpuload;
180
}
181
 
182
/* Stop measurements of the cpuload. The cyg_cpuload_t object can then
183
   be freed. */
184
externC void
185
cyg_cpuload_delete(cyg_handle_t handle) {
186
  cyg_cpuload_t * cpuload = (cyg_cpuload_t *) handle;
187
 
188
  cyg_alarm_delete(cpuload->alarmH);
189
}
190
 
191
/* Return the cpuload for the last 100ms, 1seconds and 10 second */
192
externC void
193
cyg_cpuload_get(cyg_handle_t handle,
194
                cyg_uint32 *average_point1s,
195
                cyg_uint32 *average_1s,
196
                cyg_uint32 *average_10s) {
197
 
198
  cyg_cpuload_t * cpuload = (cyg_cpuload_t *) handle;
199
  *average_point1s = cpuload->average_point1s;
200
  *average_1s = cpuload->average_1s/10;
201
  *average_10s = cpuload->average_10s/100;
202
}
203
 
204
 
205
 
206
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.