|
Packit |
577717 |
/**
|
|
Packit |
577717 |
* @file linux-lmsensors.c
|
|
Packit |
577717 |
* @author Daniel Lucio
|
|
Packit |
577717 |
* @author Joachim Protze
|
|
Packit |
577717 |
* @author Heike Jagode
|
|
Packit |
577717 |
* jagode@eecs.utk.edu
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
* @ingroup papi_components
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
* LM_SENSORS component
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
* Tested version of lm_sensors: 3.1.1
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
* @brief
|
|
Packit |
577717 |
* This file has the source code for a component that enables PAPI-C to access
|
|
Packit |
577717 |
* hardware monitoring sensors through the libsensors library. This code will
|
|
Packit |
577717 |
* dynamically create a native events table for all the sensors that can be
|
|
Packit |
577717 |
* accesed by the libsensors library.
|
|
Packit |
577717 |
* In order to learn more about libsensors, visit: (http://www.lm-sensors.org)
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
* Notes:
|
|
Packit |
577717 |
* - I used the ACPI and MX components to write this component. A lot of the
|
|
Packit |
577717 |
* code in this file mimics what other components already do.
|
|
Packit |
577717 |
* - The return values are scaled by 1000 because PAPI can not return decimals.
|
|
Packit |
577717 |
* - A call of PAPI_read can take up to 2 seconds while using lm_sensors!
|
|
Packit |
577717 |
* - Please remember that libsensors uses the GPL license.
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Headers required by libsensors */
|
|
Packit |
577717 |
#include <sensors.h>
|
|
Packit |
577717 |
#include <error.h>
|
|
Packit |
577717 |
#include <time.h>
|
|
Packit |
577717 |
#include <string.h>
|
|
Packit |
577717 |
#include <dlfcn.h>
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Headers required by PAPI */
|
|
Packit |
577717 |
#include "papi.h"
|
|
Packit |
577717 |
#include "papi_internal.h"
|
|
Packit |
577717 |
#include "papi_vector.h"
|
|
Packit |
577717 |
#include "papi_memory.h"
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/************************* DEFINES SECTION ***********************************
|
|
Packit |
577717 |
*******************************************************************************/
|
|
Packit |
577717 |
// time in usecs
|
|
Packit |
577717 |
#define LM_SENSORS_REFRESHTIME 200000
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/** Structure that stores private information of each event */
|
|
Packit |
577717 |
typedef struct _lmsensors_register
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
/* This is used by the framework.It likes it to be !=0 to do somehting */
|
|
Packit |
577717 |
unsigned int selector;
|
|
Packit |
577717 |
/* These are the only information needed to locate a libsensors event */
|
|
Packit |
577717 |
const sensors_chip_name *name;
|
|
Packit |
577717 |
int subfeat_nr;
|
|
Packit |
577717 |
} _lmsensors_register_t;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* The following structures mimic the ones used by other components. It is more
|
|
Packit |
577717 |
* convenient to use them like that as programming with PAPI makes specific
|
|
Packit |
577717 |
* assumptions for them.
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/** This structure is used to build the table of events */
|
|
Packit |
577717 |
typedef struct _lmsensors_native_event_entry
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
_lmsensors_register_t resources;
|
|
Packit |
577717 |
char name[PAPI_MAX_STR_LEN];
|
|
Packit |
577717 |
char description[PAPI_MAX_STR_LEN];
|
|
Packit |
577717 |
unsigned int count;
|
|
Packit |
577717 |
} _lmsensors_native_event_entry_t;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
typedef struct _lmsensors_reg_alloc
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
_lmsensors_register_t ra_bits;
|
|
Packit |
577717 |
} _lmsensors_reg_alloc_t;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
typedef struct _lmsensors_control_state
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
long_long lastupdate;
|
|
Packit |
577717 |
} _lmsensors_control_state_t;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
typedef struct _lmsensors_context
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
_lmsensors_control_state_t state;
|
|
Packit |
577717 |
} _lmsensors_context_t;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/************************* GLOBALS SECTION ***********************************
|
|
Packit |
577717 |
*******************************************************************************/
|
|
Packit |
577717 |
/* This table contains the LM_SENSORS native events */
|
|
Packit |
577717 |
static _lmsensors_native_event_entry_t *lm_sensors_native_table;
|
|
Packit |
577717 |
/* number of events in the table*/
|
|
Packit |
577717 |
static int num_events = 0;
|
|
Packit |
577717 |
static long_long *cached_counts = NULL; // used for caching readings
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static int (*sensors_initPtr)(FILE *input);
|
|
Packit |
577717 |
static void (*sensors_cleanupPtr)(void);
|
|
Packit |
577717 |
static int (*sensors_snprintf_chip_namePtr)(char *str, size_t size,
|
|
Packit |
577717 |
const sensors_chip_name *chip);
|
|
Packit |
577717 |
static char *(*sensors_get_labelPtr)(const sensors_chip_name *name, const sensors_feature *feature);
|
|
Packit |
577717 |
static int (*sensors_get_valuePtr)(const sensors_chip_name *name, int subfeat_nr,
|
|
Packit |
577717 |
double *value);
|
|
Packit |
577717 |
static const sensors_chip_name *(*sensors_get_detected_chipsPtr)(const sensors_chip_name
|
|
Packit |
577717 |
*match, int *nr);
|
|
Packit |
577717 |
static const sensors_feature *(*sensors_get_featuresPtr)(const sensors_chip_name *name, int *nr);
|
|
Packit |
577717 |
static const sensors_subfeature *(*sensors_get_all_subfeaturesPtr)(const sensors_chip_name *name,
|
|
Packit |
577717 |
const sensors_feature *feature, int *nr);
|
|
Packit |
577717 |
|
|
Packit |
577717 |
// file handles used to access lmsensors libraries with dlopen
|
|
Packit |
577717 |
static void* dl1 = NULL;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static int link_lmsensors_libraries ();
|
|
Packit |
577717 |
|
|
Packit |
577717 |
papi_vector_t _lmsensors_vector;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/******************************************************************************
|
|
Packit |
577717 |
******** BEGIN FUNCTIONS USED INTERNALLY SPECIFIC TO THIS COMPONENT ********
|
|
Packit |
577717 |
*****************************************************************************/
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* Counts number of events available in this system
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static unsigned
|
|
Packit |
577717 |
detectSensors( void )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
unsigned id = 0;
|
|
Packit |
577717 |
int chip_nr = 0;
|
|
Packit |
577717 |
const sensors_chip_name *chip_name;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Loop through all the chips, features, subfeatures found */
|
|
Packit |
577717 |
while ( ( chip_name =
|
|
Packit |
577717 |
sensors_get_detected_chipsPtr( NULL, &chip_nr ) ) != NULL ) {
|
|
Packit |
577717 |
int a = 0, b;
|
|
Packit |
577717 |
const sensors_feature *feature;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
while ( ( feature = sensors_get_featuresPtr( chip_name, &a ) ) ) {
|
|
Packit |
577717 |
b = 0;
|
|
Packit |
577717 |
while ( ( sensors_get_all_subfeaturesPtr( chip_name, feature,
|
|
Packit |
577717 |
&b ) ) ) {
|
|
Packit |
577717 |
id++;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return id;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* Create the native events for particulare component (!= 0)
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static unsigned
|
|
Packit |
577717 |
createNativeEvents( void )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
unsigned id = 0;
|
|
Packit |
577717 |
unsigned int count;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
int chip_nr = 0;
|
|
Packit |
577717 |
const sensors_chip_name *chip_name;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* component name and description */
|
|
Packit |
577717 |
strcpy( _lmsensors_vector.cmp_info.short_name, "lm_sensors" );
|
|
Packit |
577717 |
strcpy( _lmsensors_vector.cmp_info.description,
|
|
Packit |
577717 |
"lm-sensors provides tools for monitoring the hardware health" );
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Loop through all the chips found */
|
|
Packit |
577717 |
while ( ( chip_name =
|
|
Packit |
577717 |
sensors_get_detected_chipsPtr( NULL, &chip_nr ) ) != NULL ) {
|
|
Packit |
577717 |
int a, b;
|
|
Packit |
577717 |
const sensors_feature *feature;
|
|
Packit |
577717 |
const sensors_subfeature *sub;
|
|
Packit |
577717 |
char chipnamestring[PAPI_MIN_STR_LEN];
|
|
Packit |
577717 |
|
|
Packit |
577717 |
// lm_sensors_native_table[id].count = 0;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* get chip name from its internal representation */
|
|
Packit |
577717 |
sensors_snprintf_chip_namePtr( chipnamestring,
|
|
Packit |
577717 |
PAPI_MIN_STR_LEN, chip_name );
|
|
Packit |
577717 |
|
|
Packit |
577717 |
a = 0;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Loop through all the features found */
|
|
Packit |
577717 |
while ( ( feature = sensors_get_featuresPtr( chip_name, &a ) ) ) {
|
|
Packit |
577717 |
char *featurelabel;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
if ( !( featurelabel = sensors_get_labelPtr( chip_name, feature ))) {
|
|
Packit |
577717 |
fprintf( stderr, "ERROR: Can't get label of feature %s!\n",
|
|
Packit |
577717 |
feature->name );
|
|
Packit |
577717 |
continue;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
b = 0;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Loop through all the subfeatures found */
|
|
Packit |
577717 |
while ((sub=sensors_get_all_subfeaturesPtr(chip_name,feature,&b))) {
|
|
Packit |
577717 |
|
|
Packit |
577717 |
count = 0;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Save native event data */
|
|
Packit |
577717 |
sprintf( lm_sensors_native_table[id].name, "%s.%s.%s",
|
|
Packit |
577717 |
chipnamestring, featurelabel, sub->name );
|
|
Packit |
577717 |
|
|
Packit |
577717 |
strncpy( lm_sensors_native_table[id].description,
|
|
Packit |
577717 |
lm_sensors_native_table[id].name, PAPI_MAX_STR_LEN );
|
|
Packit |
577717 |
lm_sensors_native_table[id].description[PAPI_MAX_STR_LEN-1] = '\0';
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* The selector has to be !=0 . Starts with 1 */
|
|
Packit |
577717 |
lm_sensors_native_table[id].resources.selector = id + 1;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Save the actual references to this event */
|
|
Packit |
577717 |
lm_sensors_native_table[id].resources.name = chip_name;
|
|
Packit |
577717 |
lm_sensors_native_table[id].resources.subfeat_nr = sub->number;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
count = sub->number;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* increment the table index counter */
|
|
Packit |
577717 |
id++;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
// lm_sensors_native_table[id].count = count + 1;
|
|
Packit |
577717 |
free( featurelabel );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Return the number of events created */
|
|
Packit |
577717 |
return id;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* Returns the value of the event with index 'i' in lm_sensors_native_table
|
|
Packit |
577717 |
* This value is scaled by 1000 to cope with the lack to return decimal numbers
|
|
Packit |
577717 |
* with PAPI
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static long_long
|
|
Packit |
577717 |
getEventValue( unsigned event_id )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
double value;
|
|
Packit |
577717 |
int res;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
res = sensors_get_valuePtr( lm_sensors_native_table[event_id].resources.name,
|
|
Packit |
577717 |
lm_sensors_native_table[event_id].resources.
|
|
Packit |
577717 |
subfeat_nr, &value );
|
|
Packit |
577717 |
|
|
Packit |
577717 |
if ( res < 0 ) {
|
|
Packit |
577717 |
fprintf( stderr, "libsensors(): Could not read event #%d!\n",
|
|
Packit |
577717 |
event_id );
|
|
Packit |
577717 |
return -1;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return ( ( long_long ) ( value * 1000 ) );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*****************************************************************************
|
|
Packit |
577717 |
******************* BEGIN PAPI's COMPONENT REQUIRED FUNCTIONS *************
|
|
Packit |
577717 |
*****************************************************************************/
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* This is called whenever a thread is initialized
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_init_thread( hwd_context_t *ctx )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
( void ) ctx;
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Initialize hardware counters, setup the function vector table
|
|
Packit |
577717 |
* and get hardware information, this routine is called when the
|
|
Packit |
577717 |
* PAPI process is initialized (IE PAPI_library_init)
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_init_component( int cidx )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
int res;
|
|
Packit |
577717 |
(void) cidx;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* link in all the lmsensor libraries and resolve the symbols we need to use */
|
|
Packit |
577717 |
if (link_lmsensors_libraries() != PAPI_OK) {
|
|
Packit |
577717 |
SUBDBG ("Dynamic link of lmsensors libraries failed, component will be disabled.\n");
|
|
Packit |
577717 |
SUBDBG ("See disable reason in papi_component_avail output for more details.\n");
|
|
Packit |
577717 |
return (PAPI_ENOSUPP);
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Initialize libsensors library */
|
|
Packit |
577717 |
if ( ( res = sensors_initPtr( NULL ) ) != 0 ) {
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"Cannot enable libsensors",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return res;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Create dyanmic events table */
|
|
Packit |
577717 |
num_events = detectSensors( );
|
|
Packit |
577717 |
SUBDBG("Found %d sensors\n",num_events);
|
|
Packit |
577717 |
|
|
Packit |
577717 |
_lmsensors_vector.cmp_info.num_mpx_cntrs = num_events;
|
|
Packit |
577717 |
_lmsensors_vector.cmp_info.num_cntrs = num_events;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
if ( ( lm_sensors_native_table =
|
|
Packit |
577717 |
calloc( num_events, sizeof ( _lmsensors_native_event_entry_t )))
|
|
Packit |
577717 |
== NULL ) {
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"Could not malloc room",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return PAPI_ENOMEM;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
cached_counts = (long long*) calloc(num_events, sizeof(long long));
|
|
Packit |
577717 |
|
|
Packit |
577717 |
if (cached_counts == NULL) {
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"Could not malloc room",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return PAPI_ENOMEM;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
if ( ( unsigned ) num_events != createNativeEvents( ) ) {
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"LM_SENSOR number mismatch",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return PAPI_ECMP;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
_lmsensors_vector.cmp_info.num_native_events=num_events;
|
|
Packit |
577717 |
_lmsensors_vector.cmp_info.num_cntrs=num_events;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* Link the necessary lmsensors libraries to use the lmsensors
|
|
Packit |
577717 |
* component. If any of them can not be found, then the lmsensors
|
|
Packit |
577717 |
* component will just be disabled. This is done at runtime so that a
|
|
Packit |
577717 |
* version of PAPI built with the Infiniband component can be
|
|
Packit |
577717 |
* installed and used on systems which have the lmsensors libraries
|
|
Packit |
577717 |
* installed and on systems where these libraries are not installed.
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
link_lmsensors_libraries ()
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
/* Need to link in the lmsensors libraries, if not found disable the component */
|
|
Packit |
577717 |
dl1 = dlopen("libsensors.so", RTLD_NOW | RTLD_GLOBAL);
|
|
Packit |
577717 |
if (!dl1)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"lmsensors library libsensors.so not found.",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return ( PAPI_ENOSUPP );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
sensors_initPtr = dlsym(dl1, "sensors_init");
|
|
Packit |
577717 |
if (dlerror() != NULL)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"lmsensor function sensors_init.",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return ( PAPI_ENOSUPP );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
sensors_cleanupPtr = dlsym(dl1, "sensors_cleanup");
|
|
Packit |
577717 |
if (dlerror() != NULL)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"lmsensor function sensors_cleanup.",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return ( PAPI_ENOSUPP );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
sensors_snprintf_chip_namePtr = dlsym(dl1, "sensors_snprintf_chip_name");
|
|
Packit |
577717 |
if (dlerror() != NULL)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"lmsensor function sensors_snprintf_chip_name.",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return ( PAPI_ENOSUPP );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
sensors_get_labelPtr = dlsym(dl1, "sensors_get_label");
|
|
Packit |
577717 |
if (dlerror() != NULL)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"lmsensor function sensors_get_label.",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return ( PAPI_ENOSUPP );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
sensors_get_valuePtr = dlsym(dl1, "sensors_get_value");
|
|
Packit |
577717 |
if (dlerror() != NULL)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"lmsensor function sensors_get_value.",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return ( PAPI_ENOSUPP );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
sensors_get_detected_chipsPtr = dlsym(dl1, "sensors_get_detected_chips");
|
|
Packit |
577717 |
if (dlerror() != NULL)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"lmsensor function sensors_get_detected_chips.",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return ( PAPI_ENOSUPP );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
sensors_get_featuresPtr = dlsym(dl1, "sensors_get_features");
|
|
Packit |
577717 |
if (dlerror() != NULL)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"lmsensor function sensors_get_features.",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return ( PAPI_ENOSUPP );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
sensors_get_all_subfeaturesPtr = dlsym(dl1, "sensors_get_all_subfeatures");
|
|
Packit |
577717 |
if (dlerror() != NULL)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
strncpy(_lmsensors_vector.cmp_info.disabled_reason,
|
|
Packit |
577717 |
"lmsensor function sensors_get_all_subfeatures.",PAPI_MAX_STR_LEN);
|
|
Packit |
577717 |
return ( PAPI_ENOSUPP );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return ( PAPI_OK );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* Control of counters (Reading/Writing/Starting/Stopping/Setup)
|
|
Packit |
577717 |
* functions
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_init_control_state( hwd_control_state_t *ctl )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
int i;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
for ( i = 0; i < num_events; i++ )
|
|
Packit |
577717 |
cached_counts[i] = getEventValue( i );
|
|
Packit |
577717 |
|
|
Packit |
577717 |
( ( _lmsensors_control_state_t * ) ctl )->lastupdate =
|
|
Packit |
577717 |
PAPI_get_real_usec( );
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_start( hwd_context_t *ctx, hwd_control_state_t *ctl )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
( void ) ctx;
|
|
Packit |
577717 |
( void ) ctl;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_stop( hwd_context_t *ctx, hwd_control_state_t *ctl )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
( void ) ctx;
|
|
Packit |
577717 |
( void ) ctl;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_read( hwd_context_t *ctx, hwd_control_state_t *ctl,
|
|
Packit |
577717 |
long_long ** events, int flags )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
( void ) ctx;
|
|
Packit |
577717 |
( void ) flags;
|
|
Packit |
577717 |
long long start = PAPI_get_real_usec( );
|
|
Packit |
577717 |
int i;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
_lmsensors_control_state_t *control=(_lmsensors_control_state_t *)ctl;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
if ( start - control->lastupdate > 200000 ) { // cache refresh
|
|
Packit |
577717 |
|
|
Packit |
577717 |
for ( i = 0; i < num_events; i++ ) {
|
|
Packit |
577717 |
cached_counts[i] = getEventValue( i );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
control->lastupdate = PAPI_get_real_usec( );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
*events = cached_counts;
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_shutdown_component( void )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
if (cached_counts)
|
|
Packit |
577717 |
free(cached_counts);
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* Call the libsensors cleaning function before leaving */
|
|
Packit |
577717 |
sensors_cleanupPtr( );
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_shutdown_thread( hwd_context_t *ctx )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
( void ) ctx;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* This function sets various options in the component
|
|
Packit |
577717 |
* The valid codes being passed in are PAPI_SET_DEFDOM,
|
|
Packit |
577717 |
* PAPI_SET_DOMAIN, PAPI_SETDEFGRN, PAPI_SET_GRANUL * and PAPI_SET_INHERIT
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_ctl( hwd_context_t *ctx, int code, _papi_int_option_t *option )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
( void ) ctx;
|
|
Packit |
577717 |
( void ) code;
|
|
Packit |
577717 |
( void ) option;
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_update_control_state( hwd_control_state_t *ctl,
|
|
Packit |
577717 |
NativeInfo_t * native,
|
|
Packit |
577717 |
int count,
|
|
Packit |
577717 |
hwd_context_t *ctx )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
int i, index;
|
|
Packit |
577717 |
( void ) ctx;
|
|
Packit |
577717 |
( void ) ctl;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
for ( i = 0; i < count; i++ ) {
|
|
Packit |
577717 |
index = native[i].ni_event;
|
|
Packit |
577717 |
native[i].ni_position =
|
|
Packit |
577717 |
lm_sensors_native_table[index].resources.selector - 1;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* As I understand it, all data reported by these interfaces will be system wide
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_set_domain( hwd_control_state_t *ctl, int domain )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
(void) ctl;
|
|
Packit |
577717 |
if ( PAPI_DOM_ALL != domain )
|
|
Packit |
577717 |
return ( PAPI_EINVAL );
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return ( PAPI_OK );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_reset( hwd_context_t *ctx, hwd_control_state_t *ctl )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
( void ) ctx;
|
|
Packit |
577717 |
( void ) ctl;
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* Native Event functions
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_ntv_enum_events( unsigned int *EventCode, int modifier )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
|
|
Packit |
577717 |
switch ( modifier ) {
|
|
Packit |
577717 |
case PAPI_ENUM_FIRST:
|
|
Packit |
577717 |
*EventCode = 0;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
break;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
case PAPI_ENUM_EVENTS:
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
int index = *EventCode;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
if ( index < num_events - 1 ) {
|
|
Packit |
577717 |
*EventCode = *EventCode + 1;
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
} else
|
|
Packit |
577717 |
return PAPI_ENOEVNT;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
break;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
default:
|
|
Packit |
577717 |
return PAPI_EINVAL;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
return PAPI_EINVAL;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_ntv_code_to_name( unsigned int EventCode, char *name, int len )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
int index = EventCode;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
if (index>=0 && index
|
|
Packit |
577717 |
strncpy( name, lm_sensors_native_table[index].name, len );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static int
|
|
Packit |
577717 |
_lmsensors_ntv_code_to_descr( unsigned int EventCode, char *name, int len )
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
int index = EventCode;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
if (index>=0 && index
|
|
Packit |
577717 |
strncpy( name, lm_sensors_native_table[index].description, len );
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
return PAPI_OK;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
papi_vector_t _lmsensors_vector = {
|
|
Packit |
577717 |
.cmp_info = {
|
|
Packit |
577717 |
/* component information (unspecified values are initialized to 0) */
|
|
Packit |
577717 |
.name = "lmsensors",
|
|
Packit |
577717 |
.short_name = "lmsensors",
|
|
Packit |
577717 |
.version = "5.0",
|
|
Packit |
577717 |
.description = "Linux LMsensor statistics",
|
|
Packit |
577717 |
.num_mpx_cntrs = 0,
|
|
Packit |
577717 |
.num_cntrs = 0,
|
|
Packit |
577717 |
.default_domain = PAPI_DOM_ALL,
|
|
Packit |
577717 |
.default_granularity = PAPI_GRN_SYS,
|
|
Packit |
577717 |
.available_granularities = PAPI_GRN_SYS,
|
|
Packit |
577717 |
.hardware_intr_sig = PAPI_INT_SIGNAL,
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* component specific cmp_info initializations */
|
|
Packit |
577717 |
.fast_real_timer = 0,
|
|
Packit |
577717 |
.fast_virtual_timer = 0,
|
|
Packit |
577717 |
.attach = 0,
|
|
Packit |
577717 |
.attach_must_ptrace = 0,
|
|
Packit |
577717 |
.available_domains = PAPI_DOM_USER | PAPI_DOM_KERNEL,
|
|
Packit |
577717 |
},
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* sizes of framework-opaque component-private structures */
|
|
Packit |
577717 |
.size = {
|
|
Packit |
577717 |
.context = sizeof ( _lmsensors_context_t ),
|
|
Packit |
577717 |
.control_state = sizeof ( _lmsensors_control_state_t ),
|
|
Packit |
577717 |
.reg_value = sizeof ( _lmsensors_register_t ),
|
|
Packit |
577717 |
.reg_alloc = sizeof ( _lmsensors_reg_alloc_t ),
|
|
Packit |
577717 |
},
|
|
Packit |
577717 |
/* function pointers in this component */
|
|
Packit |
577717 |
.init_thread = _lmsensors_init_thread,
|
|
Packit |
577717 |
.init_component = _lmsensors_init_component,
|
|
Packit |
577717 |
.init_control_state = _lmsensors_init_control_state,
|
|
Packit |
577717 |
.start = _lmsensors_start,
|
|
Packit |
577717 |
.stop = _lmsensors_stop,
|
|
Packit |
577717 |
.read = _lmsensors_read,
|
|
Packit |
577717 |
.shutdown_thread = _lmsensors_shutdown_thread,
|
|
Packit |
577717 |
.shutdown_component = _lmsensors_shutdown_component,
|
|
Packit |
577717 |
.ctl = _lmsensors_ctl,
|
|
Packit |
577717 |
.update_control_state = _lmsensors_update_control_state,
|
|
Packit |
577717 |
.set_domain = _lmsensors_set_domain,
|
|
Packit |
577717 |
.reset = _lmsensors_reset,
|
|
Packit |
577717 |
|
|
Packit |
577717 |
.ntv_enum_events = _lmsensors_ntv_enum_events,
|
|
Packit |
577717 |
.ntv_code_to_name = _lmsensors_ntv_code_to_name,
|
|
Packit |
577717 |
.ntv_code_to_descr = _lmsensors_ntv_code_to_descr,
|
|
Packit |
577717 |
};
|