PAPI  5.3.2.0
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
papi_hl.c
Go to the documentation of this file.
1 /****************************/
2 /* THIS IS OPEN SOURCE CODE */
3 /****************************/
4 
16 #include "papi.h"
17 #include "papi_internal.h"
18 #include "papi_memory.h"
19 #include <string.h>
20 
21 /* high level papi functions*/
22 
23 /*
24  * Which high-level interface are we using?
25  */
26 #define HL_STOP 0
27 #define HL_START 1
28 #define HL_FLIP 2
29 #define HL_FLOP 3
30 #define HL_IPC 4
31 #define HL_EPC 5
32 #define HL_READ 6
33 #define HL_ACCUM 7
34 
38 typedef struct _HighLevelInfo
39 {
40  int EventSet;
41  short int num_evts;
42  short int running;
43  long long initial_real_time;
44  long long initial_proc_time;
45  long long last_real_time;
46  long long last_proc_time;
47  long long total_ins;
49 
50 int _hl_rate_calls( float *real_time, float *proc_time, int *events,
51  long long *values, long long *ins, float *rate, int mode );
55 int _internal_hl_read_cnts( long long *values, int array_len, int flag );
56 
57 /* CHANGE LOG:
58  - ksl 10/17/03
59  Pretty much a complete rewrite of the high level interface. Now
60  the interface is thread safe and you don't have to worry as much
61  about mixing the various high level calls.
62 
63  - dkt 11/19/01:
64  After much discussion with users and developers, removed FMA and SLOPE
65  fudge factors. SLOPE was not being used, and we decided the place to
66  apply FMA was at a higher level where there could be a better understanding
67  of platform discrepancies and code implications.
68  ALL PAPI CALLS NOW RETURN EXACTLY WHAT THE HARDWARE REPORTS
69  - dkt 08/14/01:
70  Added reinitialization of values and proc_time to new reinit code.
71  Added SLOPE and FMA constants to correct for systemic errors on a
72  platform-by-platform basis.
73  SLOPE is a factor subtracted from flpins on each call to compensate
74  for platform overhead in the call.
75  FMA is a shifter that doubles floating point counts on platforms that
76  count FMA as one op instead of two.
77  NOTE: We are making the FLAWED assumption that ALL flpins are FMA!
78  This will result in counts that are TOO HIGH on the affected platforms
79  in instances where the code is NOT mostly FMA.
80  - dkt 08/01/01:
81  NOTE: Calling semantics have changed!
82  Now, if flpins < 0 (an invalid value) a PAPI_reset is issued to reset the
83  counter values. The internal start time is also reset. This should be a
84  benign change, exept in the rare case where a user passes an uninitialized
85  (and possibly negative) value for flpins to the routine *AFTER* it has been
86  called the first time. This is unlikely, since the first call clears and
87  returns th is value.
88  - dkt 08/01/01:
89  Internal sequencing changes:
90  -- initial PAPI_get_real_usec() call moved above PAPI_start to avoid unwanted flops.
91  -- PAPI_accum() replaced with PAPI_start() / PAPI_stop pair for same reason.
92 */
93 
99 int
101 {
102  int retval;
103  HighLevelInfo *state = NULL;
104 
105  /* Only allow one thread at a time in here */
106  if ( init_level == PAPI_NOT_INITED ) {
108  if ( retval != PAPI_VER_CURRENT ) {
109  return ( retval );
110  } else {
114  }
115  }
116 
117  /*
118  * Do we have the thread specific data setup yet?
119  */
120  if ( ( retval =
121  PAPI_get_thr_specific( PAPI_HIGH_LEVEL_TLS, ( void * ) &state ) )
122  != PAPI_OK || state == NULL ) {
123  state = ( HighLevelInfo * ) papi_malloc( sizeof ( HighLevelInfo ) );
124  if ( state == NULL )
125  return ( PAPI_ENOMEM );
126 
127  memset( state, 0, sizeof ( HighLevelInfo ) );
128  state->EventSet = -1;
129 
130  if ( ( retval = PAPI_create_eventset( &state->EventSet ) ) != PAPI_OK )
131  return ( retval );
132 
133  if ( ( retval =
135  state ) ) != PAPI_OK )
136  return ( retval );
137  }
138  *outgoing = state;
139  return ( PAPI_OK );
140 }
141 
145 int
147 {
148  return ( PAPI_start( state->EventSet ) );
149 }
150 
151 void
153 {
154  state->num_evts = 0;
155  state->running = HL_STOP;
156  state->initial_real_time = -1;
157  state->initial_proc_time = -1;
158  state->total_ins = 0;
159  return;
160 }
161 
203 int
204 PAPI_flips( float *rtime, float *ptime, long long *flpins, float *mflips )
205 {
206  int retval;
207  int events = PAPI_FP_INS;
208  long long values = 0;
209 
210  if ( rtime == NULL || ptime == NULL || flpins == NULL || mflips == NULL )
211  return PAPI_EINVAL;
212 
213  retval = _hl_rate_calls( rtime, ptime, &events, &values, flpins, mflips, HL_FLIP );
214  return ( retval );
215 }
216 
258 int
259 PAPI_flops( float *rtime, float *ptime, long long *flpops, float *mflops )
260 {
261  int retval;
262  int events = PAPI_FP_OPS;
263  long long values = 0;
264 
265  if ( rtime == NULL || ptime == NULL || flpops == NULL || mflops == NULL )
266  return PAPI_EINVAL;
267 
268  retval = _hl_rate_calls( rtime, ptime, &events, &values, flpops, mflops, HL_FLOP );
269  return ( retval );
270 }
271 
315 int
316 PAPI_ipc( float *rtime, float *ptime, long long *ins, float *ipc )
317 {
318  long long values[2] = { 0, 0 };
319  int events[2] = {PAPI_TOT_INS, PAPI_TOT_CYC};
320  int retval = 0;
321 
322  if ( rtime == NULL || ptime == NULL || ins == NULL || ipc == NULL )
323  return PAPI_EINVAL;
324 
325  retval = _hl_rate_calls( rtime, ptime, events, values, ins, ipc, HL_IPC );
326  return ( retval );
327 }
328 
382 int
383 PAPI_epc( int event, float *rtime, float *ptime, long long *ref, long long *core, long long *evt, float *epc )
384 {
385  long long values[3] = { 0, 0, 0 };
387  int retval = 0;
388 
389  if ( rtime == NULL || ptime == NULL || ref == NULL ||core == NULL || evt == NULL || epc == NULL )
390  return PAPI_EINVAL;
391 
392  // if an event is provided, use it; otherwise use TOT_INS
393  if (event != 0 ) events[0] = event;
394 
395  if ( PAPI_query_event( ( int ) PAPI_REF_CYC ) != PAPI_OK )
396  events[2] = 0;
397 
398  retval = _hl_rate_calls( rtime, ptime, events, values, evt, epc, HL_EPC );
399  *core = values[1];
400  *ref = values[2];
401  return ( retval );
402 }
403 
404 int
405 _hl_rate_calls( float *real_time, float *proc_time, int *events,
406  long long *values, long long *ins, float *rate, int mode )
407 {
408  long long rt, pt; // current elapsed real and process times in usec
409  int num_events = 2;
410  int retval = 0;
411  HighLevelInfo *state = NULL;
412 
413  if ( ( retval = _internal_check_state( &state ) ) != PAPI_OK ) {
414  return ( retval );
415  }
416 
417  if ( state->running != HL_STOP && state->running != mode ) {
418  return PAPI_EINVAL;
419  }
420 
421  if ( state->running == HL_STOP ) {
422 
423  switch (mode) {
424  case HL_FLOP:
425  case HL_FLIP:
426  num_events = 1;
427  break;
428  case HL_IPC:
429  break;
430  case HL_EPC:
431  if ( events[2] != 0 ) num_events = 3;
432  break;
433  default:
434  return PAPI_EINVAL;
435  }
436  if (( retval = PAPI_add_events( state->EventSet, events, num_events )) != PAPI_OK ) {
437  _internal_cleanup_hl_info( state );
439  return retval;
440  }
441 
442  state->total_ins = 0;
445 
446  if ( ( retval = PAPI_start( state->EventSet ) ) != PAPI_OK ) {
447  return retval;
448  }
449 
450  /* Initialize the interface */
451  state->running = mode;
452  *real_time = 0.0;
453  *proc_time = 0.0;
454  *rate = 0.0;
455 
456  } else {
457  if ( ( retval = PAPI_stop( state->EventSet, values ) ) != PAPI_OK ) {
458  state->running = HL_STOP;
459  return retval;
460  }
461 
462  /* Read elapsed real and process times */
463  rt = PAPI_get_real_usec();
464  pt = PAPI_get_virt_usec();
465 
466  /* Convert to seconds with multiplication because it is much faster */
467  *real_time = ((float)( rt - state->initial_real_time )) * .000001;
468  *proc_time = ((float)( pt - state->initial_proc_time )) * .000001;
469 
470  state->total_ins += values[0];
471 
472  switch (mode) {
473  case HL_FLOP:
474  case HL_FLIP:
475  /* Calculate MFLOP and MFLIP rates */
476  if ( pt > 0 ) {
477  *rate = (float)values[0] / (pt - state->last_proc_time);
478  } else *rate = 0;
479  break;
480  case HL_IPC:
481  case HL_EPC:
482  /* Calculate IPC */
483  if (values[1]!=0) {
484  *rate = (float) ((float)values[0] / (float) ( values[1]));
485  }
486  break;
487  default:
488  return PAPI_EINVAL;
489  }
490  state->last_real_time = rt;
491  state->last_proc_time = pt;
492 
493  if ( ( retval = PAPI_start( state->EventSet ) ) != PAPI_OK ) {
494  state->running = HL_STOP;
495  return retval;
496  }
497  }
498  *ins = state->total_ins;
499  return PAPI_OK;
500 }
501 
536 int
538 {
539  int retval;
540  HighLevelInfo *tmp = NULL;
541 
542  /* Make sure the Library is initialized, etc... */
543  if ( ( retval = _internal_check_state( &tmp ) ) != PAPI_OK )
544  return ( retval );
545 
546  return ( PAPI_get_opt( PAPI_MAX_HWCTRS, NULL ) );
547 }
548 
592 int
593 PAPI_start_counters( int *events, int array_len )
594 {
595  int i, retval;
596  HighLevelInfo *state = NULL;
597 
598  if ( events == NULL || array_len <= 0 )
599  return PAPI_EINVAL;
600 
601  if ( ( retval = _internal_check_state( &state ) ) != PAPI_OK )
602  return ( retval );
603 
604  if ( state->running != 0 )
605  return ( PAPI_EINVAL );
606 
607  /* load events to the new EventSet */
608  for ( i = 0; i < array_len; i++ ) {
609  retval = PAPI_add_event( state->EventSet, events[i] );
610  if ( retval == PAPI_EISRUN )
611  return ( retval );
612 
613  if ( retval ) {
614  /* remove any prior events that may have been added
615  * and cleanup the high level information
616  */
617  _internal_cleanup_hl_info( state );
619  return ( retval );
620  }
621  }
622  /* start the EventSet */
623  if ( ( retval = _internal_start_hl_counters( state ) ) == PAPI_OK ) {
624  state->running = HL_START;
625  state->num_evts = ( short ) array_len;
626  }
627  return ( retval );
628 }
629 
630 /*========================================================================*/
631 /* int PAPI_read_counters(long long *values, int array_len) */
632 /* */
633 /* Read the running counters into the values array. This call */
634 /* implicitly initializes the internal counters to zero and allows */
635 /* them continue to run upon return. */
636 /*========================================================================*/
637 
638 int
639 _internal_hl_read_cnts( long long *values, int array_len, int flag )
640 {
641  int retval;
642  HighLevelInfo *state = NULL;
643 
644  if ( ( retval = _internal_check_state( &state ) ) != PAPI_OK )
645  return ( retval );
646 
647  if ( state->running != HL_START || array_len < state->num_evts )
648  return ( PAPI_EINVAL );
649 
650  if ( flag == HL_ACCUM )
651  return ( PAPI_accum( state->EventSet, values ) );
652  else if ( flag == HL_READ ) {
653  if ( ( retval = PAPI_read( state->EventSet, values ) ) != PAPI_OK )
654  return ( retval );
655  return ( PAPI_reset( state->EventSet ) );
656  }
657 
658  /* Invalid flag passed in */
659  return ( PAPI_EINVAL );
660 }
661 
705 int
706 PAPI_read_counters( long long *values, int array_len )
707 {
708  return ( _internal_hl_read_cnts( values, array_len, HL_READ ) );
709 }
710 
711 
755 int
756 PAPI_accum_counters( long long *values, int array_len )
757 {
758  if ( values == NULL || array_len <= 0 )
759  return PAPI_EINVAL;
760 
761  return ( _internal_hl_read_cnts( values, array_len, HL_ACCUM ) );
762 }
763 
802 int
803 PAPI_stop_counters( long long *values, int array_len )
804 {
805  int retval;
806  HighLevelInfo *state = NULL;
807 
808  if ( ( retval = _internal_check_state( &state ) ) != PAPI_OK )
809  return ( retval );
810 
811  if ( state->running == 0 )
812  return ( PAPI_ENOTRUN );
813 
814  if ( state->running == HL_START ) {
815  if ( array_len < state->num_evts || values == NULL) {
816  return ( PAPI_EINVAL );
817  } else {
818  retval = PAPI_stop( state->EventSet, values );
819  }
820  }
821 
822  if ( state->running > HL_START ) {
823  long long tmp_values[3];
824  retval = PAPI_stop( state->EventSet, tmp_values );
825  }
826 
827  if ( retval == PAPI_OK ) {
828  _internal_cleanup_hl_info( state );
830  }
831  APIDBG( "PAPI_stop_counters returns %d\n", retval );
832  return retval;
833 }
834 
835 void
837 {
838  HighLevelInfo *state = NULL;
839 
840  if ( PAPI_get_thr_specific( PAPI_HIGH_LEVEL_TLS, ( void * ) &state ) ==
841  PAPI_OK ) {
842  if ( state )
843  papi_free( state );
844  }
845 }
memset(eventId, 0, size)
int PAPI_stop(int EventSet, long long *values)
Definition: papi.c:2232
int _internal_hl_read_cnts(long long *values, int array_len, int flag)
Definition: papi_hl.c:639
long long initial_proc_time
Definition: papi_hl.c:44
#define PAPI_ENOMEM
Definition: fpapi.h:107
int PAPI_add_event(int EventSet, int EventCode)
Definition: papi.c:1604
long long PAPI_get_virt_usec(void)
Definition: papi.c:6246
int PAPI_reset(int EventSet)
Definition: papi.c:2377
long long initial_real_time
Definition: papi_hl.c:43
#define HL_FLOP
Definition: papi_hl.c:29
#define papi_free(a)
Definition: papi_memory.h:35
short int num_evts
Definition: papi_hl.c:41
int PAPI_ipc(float *rtime, float *ptime, long long *ins, float *ipc)
Definition: papi_hl.c:316
#define papi_malloc(a)
Definition: papi_memory.h:34
#define PAPI_TOT_INS
Definition: fpapi.h:185
int PAPI_flops(float *rtime, float *ptime, long long *flpops, float *mflops)
Definition: papi_hl.c:259
#define PAPI_EISRUN
Definition: fpapi.h:115
int PAPI_accum_counters(long long *values, int array_len)
Definition: papi_hl.c:756
int num_events
device[deviceId] domain[domainId] event
Definition: linux-cuda.c:306
int _internal_check_state(HighLevelInfo **state)
Definition: papi_hl.c:100
return PAPI_OK
Definition: linux-nvml.c:458
#define PAPI_FP_OPS
Definition: fpapi.h:237
return PAPI_EINVAL
Definition: linux-nvml.c:408
#define PAPI_REF_CYC
Definition: fpapi.h:242
#define HL_EPC
Definition: papi_hl.c:31
int PAPI_add_events(int EventSet, int *Events, int number)
Definition: papi.c:5720
Return codes and api definitions.
#define APIDBG(format, args...)
Definition: papi_debug.h:64
#define HL_READ
Definition: papi_hl.c:32
#define HL_STOP
Definition: papi_hl.c:26
int PAPI_flips(float *rtime, float *ptime, long long *flpins, float *mflips)
Definition: papi_hl.c:204
#define HL_IPC
Definition: papi_hl.c:30
int PAPI_epc(int event, float *rtime, float *ptime, long long *ref, long long *core, long long *evt, float *epc)
Definition: papi_hl.c:383
int PAPI_get_thr_specific(int tag, void **ptr)
Definition: papi.c:357
int PAPI_accum(int EventSet, long long *values)
Definition: papi.c:2662
void _papi_hwi_shutdown_highlevel()
Definition: papi_hl.c:836
int PAPI_library_init(int version)
Definition: papi.c:495
int i
Definition: fileop.c:140
inline_static int _papi_hwi_lock(int lck)
Definition: threads.h:64
#define PAPI_MAX_HWCTRS
Definition: fpapi.h:58
#define PAPI_TOT_CYC
Definition: fpapi.h:194
int PAPI_stop_counters(long long *values, int array_len)
Definition: papi_hl.c:803
int PAPI_get_opt(int option, PAPI_option_t *ptr)
Definition: papi.c:4041
#define HL_ACCUM
Definition: papi_hl.c:33
long long last_proc_time
Definition: papi_hl.c:46
int _internal_start_hl_counters(HighLevelInfo *state)
Definition: papi_hl.c:146
#define HL_START
Definition: papi_hl.c:27
inline_static int _papi_hwi_unlock(int lck)
Definition: threads.h:78
#define PAPI_VER_CURRENT
Definition: fpapi.h:14
char events[MAX_EVENTS][BUFSIZ]
int _hl_rate_calls(float *real_time, float *proc_time, int *events, long long *values, long long *ins, float *rate, int mode)
Definition: papi_hl.c:405
child_stat flag
Definition: iozone.c:12951
#define PAPI_FP_INS
Definition: fpapi.h:187
int PAPI_cleanup_eventset(int EventSet)
Definition: papi.c:2805
int PAPI_create_eventset(int *EventSet)
Definition: papi.c:1406
void _internal_cleanup_hl_info(HighLevelInfo *state)
Definition: papi_hl.c:152
short int running
Definition: papi_hl.c:42
int PAPI_query_event(int EventCode)
Definition: papi.c:696
#define HL_FLIP
Definition: papi_hl.c:28
long long PAPI_get_real_usec(void)
Definition: papi.c:6138
#define HIGHLEVEL_LOCK
Definition: papi_internal.h:88
int PAPI_set_thr_specific(int tag, void *ptr)
Definition: papi.c:433
int PAPI_read_counters(long long *values, int array_len)
Definition: papi_hl.c:706
#define PAPI_HIGH_LEVEL_INITED
Definition: fpapi.h:19
child_idents[x-1] state
Definition: iozone.c:21341
#define PAPI_ENOTRUN
Definition: fpapi.h:114
int PAPI_num_counters(void)
Definition: papi_hl.c:537
int PAPI_start_counters(int *events, int array_len)
Definition: papi_hl.c:593
long long total_ins
Definition: papi_hl.c:47
long long last_real_time
Definition: papi_hl.c:45
int EventSet
Definition: papi_hl.c:40
int PAPI_read(int EventSet, long long *values)
Definition: papi.c:2476
int PAPI_start(int EventSet)
Definition: papi.c:2026
int init_level
Definition: papi_internal.c:54
static long long values[NUM_EVENTS]
Definition: init_fini.c:10
ssize_t retval
Definition: libasync.c:338
long long tmp
Definition: iozone.c:12031
#define PAPI_NOT_INITED
Definition: fpapi.h:17
#define PAPI_HIGH_LEVEL_TLS
Definition: papi.h:319