PAPI 7.1.0.0
Loading...
Searching...
No Matches
linux-emon.c
Go to the documentation of this file.
1/****************************/
2/* THIS IS OPEN SOURCE CODE */
3/****************************/
4
16#include <stdint.h>
17#include <string.h>
18#include "papi.h"
19#include "papi_internal.h"
20#include "papi_vector.h"
21#include "papi_memory.h"
22#include "extras.h"
23
24#define EMON_DEFINE_GLOBALS
25#include <hwi/include/bqc/A2_inlines.h>
26#include <spi/include/emon/emon.h> // the emon library header file (no linking required)
27
28#define EMON_MAX_COUNTERS 8
29#define EMON_TOTAL_EVENTS 8
30
31#ifndef DEBUG
32#define EMONDBG( fmt, args...) do {} while(0)
33#else
34#define EMONDBG( fmt, args... ) do { printf("%s:%d\t"fmt, __func__, __LINE__, ##args); } while(0)
35#endif
36
37/* Stores private information for each event */
38typedef struct EMON_register
39{
40 unsigned int selector;
41 /* Signifies which counter slot is being used */
42 /* Indexed from 1 as 0 has a special meaning */
44
46/* The contents of this structure will vary based on */
47/* your component, however having name and description */
48/* fields are probably useful. */
49typedef struct EMON_native_event_entry
50{
52 char *name;
56
57
58/* Used when doing register allocation */
59typedef struct EMON_reg_alloc
60{
63
64typedef struct EMON_overflow
65{
69
70/* Holds control flags */
71typedef struct EMON_control_state
72{
73 int count;
74 long long counters[EMON_MAX_COUNTERS];
75 int being_measured[EMON_MAX_COUNTERS];
76 long long last_update;
78
79/* Holds per-thread information */
80typedef struct EMON_context
81{
84
85/* Declare our vector in advance */
87
88static void _check_EMON_error( char* emon2func, int err )
89{
90 ( void ) emon2func;
91 if ( err < 0 ) {
92 printf( "Error: EMON API function '%s' returned %d.\n",
93 emon2func, err );
94 }
95}
96
97
102{
103 {
104 .name = "DOMAIN1",
105 .description = "Chip core",
106 .resources.selector = 1,
107 .return_type = PAPI_DATATYPE_FP64,
108 },
109 {
110 .name = "DOMAIN2",
111 .description = "Chip Memory Interface and Dramm",
112 .resources.selector = 2,
113 .return_type = PAPI_DATATYPE_FP64,
114 },
115 {
116 .name = "DOMAIN3",
117 .description = "Optics",
118 .resources.selector = 3,
119 .return_type = PAPI_DATATYPE_FP64,
120 },
121 {
122 .name = "DOMAIN4",
123 .description = "Optics + PCIExpress",
124 .resources.selector = 4,
125 .return_type = PAPI_DATATYPE_FP64,
126 },
127 {
128 .name = "DOMAIN6",
129 .description = "HSS Network and Link Chip",
130 .resources.selector = 5,
131 .return_type = PAPI_DATATYPE_FP64,
132 },
133 {
134 .name = "DOMAIN8",
135 .description = "Link Chip Core",
136 .resources.selector = 6,
137 .return_type = PAPI_DATATYPE_FP64,
138 },
139 {
140 .name = "DOMAIN7",
141 .description = "Chip SRAM",
142 .resources.selector = 7,
143 .return_type = PAPI_DATATYPE_FP64,
144 },
145 { .name="EMON_DOMAIN_ALL",
146 .description = "Measures power on all domains.",
147 .resources.selector = 8,
148 .return_type = PAPI_DATATYPE_FP64,
149 },
150};
151
152
153
154
155/*****************************************************************************
156 ******************* BEGIN PAPI's COMPONENT REQUIRED FUNCTIONS *************
157 *****************************************************************************/
158
159/*
160 * This is called whenever a thread is initialized
161 */
162int
164{
165 EMONDBG( "EMON_init_thread\n" );
166
167 ( void ) ctx;
168 return PAPI_OK;
169}
170
171
172/* Initialize hardware counters, setup the function vector table
173 * and get hardware information, this routine is called when the
174 * PAPI process is initialized (IE PAPI_library_init)
175 */
176int
178{
179 int ret = 0;
181 EMONDBG( "EMON_init_component cidx = %d\n", cidx );
182 /* Setup connection with the fpga:
183 * NOTE: any other threads attempting to call into the EMON API
184 * will be turned away. */
185 ret = EMON_SetupPowerMeasurement();
186 _check_EMON_error("EMON_SetupPowerMeasurement", ret );
187
189
192
193
194 return ( PAPI_OK );
195}
196
197
198/*
199 * Control of counters (Reading/Writing/Starting/Stopping/Setup)
200 * functions
201 */
202int
204{
205 EMONDBG( "EMON_init_control_state\n" );
206
207 EMON_control_state_t * this_state = ( EMON_control_state_t * ) ptr;
208 memset( this_state, 0, sizeof ( EMON_control_state_t ) );
209
210 return PAPI_OK;
211}
212
213static int
215{
216 union {
217 long long ll;
218 double fp;
219 } return_value;
220 return_value.fp = -1;
221
222 double volts[14],amps[14];
223 double cpu = 0;
224 double dram = 0;
225 double link_chip = 0;
226 double network = 0;
227 double optics = 0;
228 double pci = 0;
229 double sram = 0;
230 unsigned k_const;
231
232 EMONDBG( "_emon_accessor, enter this_state = %x\n", this_state);
233 return_value.fp = EMON_GetPower_impl( volts, amps );
234 EMONDBG("_emon_accessor, after EMON_GetPower %lf \n", return_value.fp);
235 if ( -1 == return_value.fp ) {
236 PAPIERROR("EMON_GetPower() failed!\n");
237 return ( PAPI_ESYS );
238 }
239
240 this_state->counters[7] = return_value.ll;
241
242/* We just stuff everything in counters, there is no extra overhead here */
243 k_const = domain_info[0].k_const; /* Chip Core Voltage */
244 cpu += volts[0] * amps[0] * k_const;
245 cpu += volts[1] * amps[1] * k_const;
246
247 k_const = domain_info[1].k_const; /* Chip Core Voltage */
248 dram += volts[2] * amps[2] * k_const;
249 dram += volts[3] * amps[3] * k_const;
250
251 k_const = domain_info[2].k_const; /* Chip Core Voltage */
252 optics += volts[4] * amps[4] * k_const;
253 optics += volts[5] * amps[5] * k_const;
254
255 k_const = domain_info[3].k_const; /* Chip Core Voltage */
256 pci += volts[6] * amps[6] * k_const;
257 pci += volts[7] * amps[7] * k_const;
258
259 k_const = domain_info[4].k_const; /* Chip Core Voltage */
260 network += volts[8] * amps[8] * k_const;
261 network += volts[9] * amps[9] * k_const;
262
263 k_const = domain_info[5].k_const; /* Chip Core Voltage */
264 link_chip += volts[10] * amps[10] * k_const;
265 link_chip += volts[11] * amps[11] * k_const;
266
267 k_const = domain_info[6].k_const; /* Chip Core Voltage */
268 sram += volts[12] * amps[12] * k_const;
269 sram += volts[13] * amps[13] * k_const;
270
271 this_state->counters[0] = *(long long*)&cpu;
272 this_state->counters[1] = *(long long*)&dram;
273 this_state->counters[2] = *(long long*)&optics;
274 this_state->counters[3] = *(long long*)&pci;
275 this_state->counters[4] = *(long long*)&link_chip;
276 this_state->counters[5] = *(long long*)&network;
277 this_state->counters[6] = *(long long*)&sram;
278
279 EMONDBG("CPU = %lf\n", *(double*)&this_state->counters[0]);
280 EMONDBG("DRAM = %lf\n", *(double*)&this_state->counters[1]);
281 EMONDBG("Optics = %lf\n", *(double*)&this_state->counters[2]);
282 EMONDBG("PCI = %lf\n", *(double*)&this_state->counters[3]);
283 EMONDBG("Link Chip = %lf\n", *(double*)&this_state->counters[4]);
284 EMONDBG("Network = %lf\n", *(double*)&this_state->counters[5]);
285 EMONDBG("SRAM = %lf\n", *(double*)&this_state->counters[6]);
286 EMONDBG("TOTAL = %lf\n", *(double*)&this_state->counters[7] );
287
288 return ( PAPI_OK );
289}
290
291/*
292 *
293 */
294int
296{
297 EMONDBG( "EMON_start\n" );
298 ( void ) ctx;
299 ( void ) ptr;
300 /*EMON_control_state_t * this_state = ( EMON_control_state_t * ) ptr;*/
301
302 return ( PAPI_OK );
303}
304
305
306/*
307 *
308 */
309int
311{
312 EMONDBG( "EMON_stop\n" );
313 ( void ) ctx;
314 EMON_control_state_t * this_state = ( EMON_control_state_t * ) ptr;
315
316 return _emon_accessor( this_state );
317}
318
319
320/*
321 *
322 */
323int
325 long long ** events, int flags )
326{
327 EMONDBG( "EMON_read\n" );
328 ( void ) ctx;
329 ( void ) flags;
330 int ret;
331 EMON_control_state_t * this_state = ( EMON_control_state_t * ) ptr;
332
333 ret = _emon_accessor( this_state );
334 *events = this_state->counters;
335 return ret;
336}
337
338
339/*
340 *
341 */
342int
344{
345 EMONDBG( "EMON_shutdown_thread\n" );
346
347 ( void ) ctx;
348 return ( PAPI_OK );
349}
350
351int
353{
354 EMONDBG( "EMON_shutdown_component\n" );
355
356 return ( PAPI_OK );
357}
358
359/* This function sets various options in the component
360 * The valid codes being passed in are PAPI_SET_DEFDOM,
361 * PAPI_SET_DOMAIN, PAPI_SETDEFGRN, PAPI_SET_GRANUL * and PAPI_SET_INHERIT
362 */
363int
364EMON_ctl( hwd_context_t * ctx, int code, _papi_int_option_t * option )
365{
366 EMONDBG( "EMON_ctl\n" );
367
368 ( void ) ctx;
369 ( void ) code;
370 ( void ) option;
371 return ( PAPI_OK );
372}
373
374
375/*
376 * PAPI Cleanup Eventset
377 */
378int
380{
381 EMONDBG( "EMON_cleanup_eventset\n" );
382
383 EMON_control_state_t * this_state = ( EMON_control_state_t * ) ctrl;
384 ( void ) this_state;
385
386 return ( PAPI_OK );
387}
388
389
390/*
391 *
392 */
393int
396 hwd_context_t * ctx )
397{
398 EMONDBG( "EMON_update_control_state: count = %d\n", count );
399
400 ( void ) ctx;
401 int index, i;
402 EMON_control_state_t * this_state = ( EMON_control_state_t * ) ptr;
403 ( void ) ptr;
404
405
406
407 // otherwise, add the events to the eventset
408 for ( i = 0; i < count; i++ ) {
409 index = ( native[i].ni_event ) ;
410
411 native[i].ni_position = i;
412
413 EMONDBG("EMON_update_control_state: ADD event: i = %d, index = %d\n", i, index );
414 }
415
416 // store how many events we added to an EventSet
417 this_state->count = count;
418
419 return ( PAPI_OK );
420}
421
422
423/*
424 * As a system wide count, PAPI_DOM_ALL is all we support
425 */
426int
428{
429 EMONDBG( "EMON_set_domain\n" );
430 ( void ) cntrl;
431
432 if ( PAPI_DOM_ALL != domain )
433 return ( PAPI_EINVAL );
434
435 return ( PAPI_OK );
436}
437
438
439/*
440 *
441 */
442int
444{
445 EMONDBG( "EMON_reset\n" );
446 ( void ) ctx;
447 int retval;
448 EMON_control_state_t * this_state = ( EMON_control_state_t * ) ptr;
449 ( void ) this_state;
450 ( void ) retval;
451
452 memset( this_state->counters, 0x0, sizeof(long long) * EMON_MAX_COUNTERS);
453
454 return ( PAPI_OK );
455}
456
457
458/*
459 * Native Event functions
460 */
461int
462EMON_ntv_enum_events( unsigned int *EventCode, int modifier )
463{
464 EMONDBG( "EMON_ntv_enum_events, EventCode = %#x\n", *EventCode );
465
466 switch ( modifier ) {
467 case PAPI_ENUM_FIRST:
468 *EventCode = 0;
469
470 return ( PAPI_OK );
471 break;
472
473 case PAPI_ENUM_EVENTS:
474 {
475 int index = ( *EventCode );
476
477 if ( index < EMON_TOTAL_EVENTS ) {
478 *EventCode = *EventCode + 1;
479 return ( PAPI_OK );
480 } else {
481 return ( PAPI_ENOEVNT );
482 }
483
484 break;
485 }
486 default:
487 return ( PAPI_EINVAL );
488 }
489 return ( PAPI_EINVAL );
490}
491
492/*
493 *
494 */
495int
496EMON_ntv_code_to_name( unsigned int EventCode, char *name, int len )
497{
498 EMONDBG( "EMON_ntv_code_to_name\n" );
499 int index;
500 ( void ) name;
501 ( void ) len;
502
503 index = ( EventCode );
504
505 if ( index >= EMON_TOTAL_EVENTS || index < 0 ) {
506 return PAPI_ENOEVNT;
507 }
508
509 strncpy( name, EMON_native_table[index].name, len );
510 return ( PAPI_OK );
511}
512
513/*
514 *
515 */
516int
517EMON_ntv_name_to_code( const char *name, unsigned int *code )
518{
519 int index;
520
521 for ( index = 0; index < EMON_TOTAL_EVENTS; index++ ) {
522 if ( 0 == strcmp( name, EMON_native_table[index].name ) ) {
523 *code = index;
524 }
525 }
526 return ( PAPI_OK );
527}
528
529int
530EMON_ntv_code_to_descr( unsigned int EventCode, char *name, int len )
531{
532 EMONDBG( "EMON_ntv_code_to_descr\n" );
533 int index;
534 ( void ) name;
535 ( void ) len;
536
537 index = ( EventCode ) ;
538
539 if ( index >= EMON_TOTAL_EVENTS || index < 0 ) {
540 return PAPI_ENOEVNT;
541 }
542 strncpy( name, EMON_native_table[index].description, len );
543
544 return ( PAPI_OK );
545}
546
547
548/*
549 *
550 */
551int
552EMON_ntv_code_to_bits( unsigned int EventCode, hwd_register_t * bits )
553{
554 EMONDBG( "EMON_ntv_code_to_bits\n" );
555 ( void ) EventCode;
556 ( void ) bits;
557 return ( PAPI_OK );
558}
559
560int
561EMON_ntv_code_to_info(unsigned int EventCode, PAPI_event_info_t *info)
562{
563
564 int index = EventCode;
565
566 if ( ( index < 0) || (index >= EMON_TOTAL_EVENTS )) return PAPI_ENOEVNT;
567
568 strncpy( info->symbol, EMON_native_table[index].name,
569 sizeof(info->symbol));
570
571 strncpy( info->long_descr, EMON_native_table[index].description,
572 sizeof(info->symbol));
573
574 //strncpy( info->units, rapl_native_events[index].units,
575 //sizeof(info->units));
576
578
579 return PAPI_OK;
580}
581
582/*
583 *
584 */
586 .cmp_info = {
587 /* default component information (unspecified values are initialized to 0) */
588 .name = "EMON",
589 .short_name = "EMON",
590 .description = "Blue Gene/Q EMON component",
591 .num_native_events = EMON_MAX_COUNTERS,
592 .num_cntrs = EMON_MAX_COUNTERS,
593 .num_mpx_cntrs = EMON_MAX_COUNTERS,
594 .default_domain = PAPI_DOM_ALL,
595 .available_domains = PAPI_DOM_ALL,
596 .default_granularity = PAPI_GRN_SYS,
597 .available_granularities = PAPI_GRN_SYS,
598
599 .hardware_intr_sig = PAPI_INT_SIGNAL,
600 .hardware_intr = 1,
601
602 .kernel_multiplex = 0,
603
604 /* component specific cmp_info initializations */
605 .fast_real_timer = 0,
606 .fast_virtual_timer = 0,
607 .attach = 0,
608 .attach_must_ptrace = 0,
609 }
610 ,
611
612 /* sizes of framework-opaque component-private structures */
613 .size = {
614 .context = sizeof ( EMON_context_t ),
615 .control_state = sizeof ( EMON_control_state_t ),
616 .reg_value = sizeof ( EMON_register_t ),
617 .reg_alloc = sizeof ( EMON_reg_alloc_t ),
618 }
619 ,
620 /* function pointers in this component */
621 .init_thread = EMON_init_thread,
622 .init_component = EMON_init_component,
623 .init_control_state = EMON_init_control_state,
624 .start = EMON_start,
625 .stop = EMON_stop,
626 .read = EMON_read,
627 .shutdown_thread = EMON_shutdown_thread,
628 .shutdown_component = EMON_shutdown_component,
629 .cleanup_eventset = EMON_cleanup_eventset,
630 .ctl = EMON_ctl,
631
632 .update_control_state = EMON_update_control_state,
633 .set_domain = EMON_set_domain,
634 .reset = EMON_reset,
635
636 .ntv_enum_events = EMON_ntv_enum_events,
637 .ntv_code_to_name = EMON_ntv_code_to_name,
638 .ntv_code_to_descr = EMON_ntv_code_to_descr,
639 .ntv_code_to_bits = EMON_ntv_code_to_bits,
640 .ntv_code_to_info = EMON_ntv_code_to_info,
641};
int i
static long count
#define PAPI_ENUM_EVENTS
Definition: f90papi.h:224
#define PAPI_OK
Definition: f90papi.h:73
#define PAPI_ENUM_FIRST
Definition: f90papi.h:85
#define PAPI_ENOEVNT
Definition: f90papi.h:139
#define PAPI_DATATYPE_FP64
Definition: f90papi.h:171
#define PAPI_EINVAL
Definition: f90papi.h:115
#define PAPI_ESYS
Definition: f90papi.h:136
#define PAPI_GRN_SYS
Definition: f90papi.h:43
#define PAPI_DOM_ALL
Definition: f90papi.h:261
char events[MAX_EVENTS][BUFSIZ]
int EMON_ctl(hwd_context_t *ctx, int code, _papi_int_option_t *option)
Definition: linux-emon.c:364
int EMON_stop(hwd_context_t *ctx, hwd_control_state_t *ptr)
Definition: linux-emon.c:310
static void _check_EMON_error(char *emon2func, int err)
Definition: linux-emon.c:88
int EMON_set_domain(hwd_control_state_t *cntrl, int domain)
Definition: linux-emon.c:427
int EMON_shutdown_component(void)
Definition: linux-emon.c:352
int EMON_ntv_enum_events(unsigned int *EventCode, int modifier)
Definition: linux-emon.c:462
int EMON_update_control_state(hwd_control_state_t *ptr, NativeInfo_t *native, int count, hwd_context_t *ctx)
Definition: linux-emon.c:394
int EMON_ntv_code_to_name(unsigned int EventCode, char *name, int len)
Definition: linux-emon.c:496
int EMON_read(hwd_context_t *ctx, hwd_control_state_t *ptr, long long **events, int flags)
Definition: linux-emon.c:324
#define EMONDBG(fmt, args...)
Definition: linux-emon.c:34
int EMON_init_control_state(hwd_control_state_t *ptr)
Definition: linux-emon.c:203
static int _emon_accessor(EMON_control_state_t *this_state)
Definition: linux-emon.c:214
papi_vector_t _emon2_vector
Definition: linux-emon.c:86
int EMON_ntv_code_to_bits(unsigned int EventCode, hwd_register_t *bits)
Definition: linux-emon.c:552
int EMON_init_component(int cidx)
Definition: linux-emon.c:177
int EMON_shutdown_thread(hwd_context_t *ctx)
Definition: linux-emon.c:343
int EMON_cleanup_eventset(hwd_control_state_t *ctrl)
Definition: linux-emon.c:379
#define EMON_TOTAL_EVENTS
Definition: linux-emon.c:29
int EMON_ntv_code_to_descr(unsigned int EventCode, char *name, int len)
Definition: linux-emon.c:530
int EMON_start(hwd_context_t *ctx, hwd_control_state_t *ptr)
Definition: linux-emon.c:295
int EMON_ntv_name_to_code(const char *name, unsigned int *code)
Definition: linux-emon.c:517
int EMON_reset(hwd_context_t *ctx, hwd_control_state_t *ptr)
Definition: linux-emon.c:443
papi_vector_t _emon_vector
Definition: linux-emon.c:585
int EMON_init_thread(hwd_context_t *ctx)
Definition: linux-emon.c:163
static EMON_native_event_entry_t EMON_native_table[]
Definition: linux-emon.c:101
#define EMON_MAX_COUNTERS
Definition: linux-emon.c:28
int EMON_ntv_code_to_info(unsigned int EventCode, PAPI_event_info_t *info)
Definition: linux-emon.c:561
Return codes and api definitions.
void PAPIERROR(char *format,...)
#define PAPI_INT_SIGNAL
Definition: papi_internal.h:52
static FILE * fp
static int native
static int cidx
const char * name
Definition: rocs.c:225
EMON_control_state_t state
Definition: linux-emon.c:82
long long counters[EMON_MAX_COUNTERS]
Definition: linux-emon.c:74
long long last_update
Definition: linux-emon.c:76
Definition: linux-emon.c:50
EMON_register_t resources
Definition: linux-emon.c:51
char * name
Definition: linux-emon.c:52
char * description
Definition: linux-emon.c:53
int return_type
Definition: linux-emon.c:54
EMON_register_t ra_bits
Definition: linux-emon.c:61
unsigned int selector
Definition: linux-emon.c:40
char name[PAPI_MAX_STR_LEN]
Definition: papi.h:627
char symbol[PAPI_HUGE_STR_LEN]
Definition: papi.h:960
char long_descr[PAPI_HUGE_STR_LEN]
Definition: papi.h:963
PAPI_component_info_t cmp_info
Definition: papi_vector.h:20
int retval
Definition: zero_fork.c:53