mirror of
https://github.com/lm-sensors/lm-sensors.git
synced 2026-11-01 13:20:30 +00:00
Subject: [PATCH 1/3 v3] libsensors: Support energy and power meters
Add power and sensor meters to libsensors, with minor tweaks and documentation updates as suggested by Jean Delvare. Signed-off-by: Darrick J. Wong <djwong@us.ibm.com> git-svn-id: http://lm-sensors.org/svn/lm-sensors/branches/lm-sensors-3.0.0@5183 7894878c-1315-0410-8ee3-d5d059ff63e0
This commit is contained in:
1 parent
bcabe00237
commit
bb840c486c
4 files changed
+65
-13
No files matched your search
@@ -6,6 +6,7 @@ SVN-HEAD
|
||||
Parse the configuration file in C locale
|
||||
Late compute statements override early ones
|
||||
Support virtual hwmon devices (#2309)
|
||||
Support power and energy sensors
|
||||
pwmconfig: Don't create the configuration file before it's needed
|
||||
Don't preserve configuration file customizations
|
||||
Fix permissions of the configuration file
|
||||
|
||||
@@ -6,6 +6,16 @@ over time. This document summarizes these evolutions so that application
|
||||
authors can quickly figure out how to test for the availability of a
|
||||
given new feature.
|
||||
|
||||
0x402 lm-sensors SVN
|
||||
* Added support for power and energy sensors
|
||||
SENSORS_FEATURE_POWER = 3
|
||||
SENSORS_FEATURE_ENERGY = 4
|
||||
SENSORS_SUBFEATURE_POWER_AVERAGE
|
||||
SENSORS_SUBFEATURE_POWER_AVERAGE_HIGHEST
|
||||
SENSORS_SUBFEATURE_POWER_AVERAGE_LOWEST
|
||||
SENSORS_SUBFEATURE_POWER_AVERAGE_INTERVAL
|
||||
SENSORS_SUBFEATURE_ENERGY_INPUT
|
||||
|
||||
0x401 lm-sensors SVN
|
||||
* Added bus type "virtual":
|
||||
#define SENSORS_BUS_TYPE_VIRTUAL 4
|
||||
|
||||
@@ -132,6 +132,8 @@ typedef enum sensors_feature_type {
|
||||
SENSORS_FEATURE_IN = 0x00,
|
||||
SENSORS_FEATURE_FAN = 0x01,
|
||||
SENSORS_FEATURE_TEMP = 0x02,
|
||||
SENSORS_FEATURE_POWER = 0x03,
|
||||
SENSORS_FEATURE_ENERGY = 0x04,
|
||||
SENSORS_FEATURE_VID = 0x10,
|
||||
SENSORS_FEATURE_BEEP_ENABLE = 0x18,
|
||||
SENSORS_FEATURE_UNKNOWN = INT_MAX,
|
||||
@@ -170,6 +172,14 @@ typedef enum sensors_subfeature_type {
|
||||
SENSORS_SUBFEATURE_TEMP_OFFSET,
|
||||
SENSORS_SUBFEATURE_TEMP_BEEP,
|
||||
|
||||
SENSORS_SUBFEATURE_POWER_AVERAGE = SENSORS_FEATURE_POWER << 8,
|
||||
SENSORS_SUBFEATURE_POWER_AVERAGE_HIGHEST,
|
||||
SENSORS_SUBFEATURE_POWER_AVERAGE_LOWEST,
|
||||
|
||||
SENSORS_SUBFEATURE_POWER_AVERAGE_INTERVAL = (SENSORS_FEATURE_POWER << 8) | 0x80,
|
||||
|
||||
SENSORS_SUBFEATURE_ENERGY_INPUT = SENSORS_FEATURE_ENERGY << 8,
|
||||
|
||||
SENSORS_SUBFEATURE_VID = SENSORS_FEATURE_VID << 8,
|
||||
|
||||
SENSORS_SUBFEATURE_BEEP_ENABLE = SENSORS_FEATURE_BEEP_ENABLE << 8,
|
||||
|
||||
+44
-13
@@ -138,24 +138,33 @@ char sensors_sysfs_mount[NAME_MAX];
|
||||
|
||||
#define MAX_SENSORS_PER_TYPE 20
|
||||
#define MAX_SUBFEATURES 8
|
||||
/* Room for all 3 types (in, fan, temp) with all their subfeatures + VID
|
||||
+ misc features */
|
||||
#define MAX_SENSOR_TYPES 5
|
||||
/* Room for all 5 types (in, fan, temp, power, energy) with all their
|
||||
subfeatures + VID + misc features */
|
||||
#define ALL_POSSIBLE_SUBFEATURES \
|
||||
(MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES * 6 \
|
||||
+ MAX_SENSORS_PER_TYPE + 1)
|
||||
(MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES * \
|
||||
MAX_SENSOR_TYPES * 2 + \
|
||||
MAX_SENSORS_PER_TYPE + 1)
|
||||
|
||||
static
|
||||
int get_type_scaling(sensors_subfeature_type type)
|
||||
{
|
||||
/* Multipliers for subfeatures */
|
||||
switch (type & 0xFF80) {
|
||||
case SENSORS_SUBFEATURE_IN_INPUT:
|
||||
case SENSORS_SUBFEATURE_TEMP_INPUT:
|
||||
return 1000;
|
||||
case SENSORS_SUBFEATURE_FAN_INPUT:
|
||||
return 1;
|
||||
case SENSORS_SUBFEATURE_POWER_AVERAGE:
|
||||
case SENSORS_SUBFEATURE_ENERGY_INPUT:
|
||||
return 1000000;
|
||||
}
|
||||
|
||||
/* Multipliers for second class subfeatures
|
||||
that need their own multiplier */
|
||||
switch (type) {
|
||||
case SENSORS_SUBFEATURE_POWER_AVERAGE_INTERVAL:
|
||||
case SENSORS_SUBFEATURE_VID:
|
||||
case SENSORS_SUBFEATURE_TEMP_OFFSET:
|
||||
return 1000;
|
||||
@@ -173,6 +182,8 @@ char *get_feature_name(sensors_feature_type ftype, char *sfname)
|
||||
case SENSORS_FEATURE_IN:
|
||||
case SENSORS_FEATURE_FAN:
|
||||
case SENSORS_FEATURE_TEMP:
|
||||
case SENSORS_FEATURE_POWER:
|
||||
case SENSORS_FEATURE_ENERGY:
|
||||
underscore = strchr(sfname, '_');
|
||||
name = strndup(sfname, underscore - sfname);
|
||||
break;
|
||||
@@ -232,6 +243,19 @@ static const struct subfeature_type_match fan_matches[] = {
|
||||
{ NULL, 0 }
|
||||
};
|
||||
|
||||
static const struct subfeature_type_match power_matches[] = {
|
||||
{ "average", SENSORS_SUBFEATURE_POWER_AVERAGE },
|
||||
{ "average_highest", SENSORS_SUBFEATURE_POWER_AVERAGE_HIGHEST },
|
||||
{ "average_lowest", SENSORS_SUBFEATURE_POWER_AVERAGE_LOWEST },
|
||||
{ "average_interval", SENSORS_SUBFEATURE_POWER_AVERAGE_INTERVAL },
|
||||
{ NULL, 0 }
|
||||
};
|
||||
|
||||
static const struct subfeature_type_match energy_matches[] = {
|
||||
{ "input", SENSORS_SUBFEATURE_ENERGY_INPUT },
|
||||
{ NULL, 0 }
|
||||
};
|
||||
|
||||
static const struct subfeature_type_match cpu_matches[] = {
|
||||
{ "vid", SENSORS_SUBFEATURE_VID },
|
||||
{ NULL, 0 }
|
||||
@@ -242,6 +266,8 @@ static struct feature_type_match matches[] = {
|
||||
{ "in%d%c", in_matches },
|
||||
{ "fan%d%c", fan_matches },
|
||||
{ "cpu%d%c", cpu_matches },
|
||||
{ "power%d%c", power_matches },
|
||||
{ "energy%d%c", energy_matches },
|
||||
};
|
||||
|
||||
/* Return the subfeature type and channel number based on the subfeature
|
||||
@@ -327,10 +353,12 @@ static int sensors_read_dynamic_chip(sensors_chip_features *chip,
|
||||
|
||||
/* Adjust the channel number */
|
||||
switch (sftype & 0xFF00) {
|
||||
case SENSORS_SUBFEATURE_FAN_INPUT:
|
||||
case SENSORS_SUBFEATURE_TEMP_INPUT:
|
||||
nr--;
|
||||
break;
|
||||
case SENSORS_SUBFEATURE_FAN_INPUT:
|
||||
case SENSORS_SUBFEATURE_TEMP_INPUT:
|
||||
case SENSORS_SUBFEATURE_POWER_AVERAGE:
|
||||
case SENSORS_SUBFEATURE_ENERGY_INPUT:
|
||||
nr--;
|
||||
break;
|
||||
}
|
||||
|
||||
if (nr < 0 || nr >= MAX_SENSORS_PER_TYPE) {
|
||||
@@ -347,11 +375,12 @@ static int sensors_read_dynamic_chip(sensors_chip_features *chip,
|
||||
sorted table */
|
||||
switch (sftype) {
|
||||
case SENSORS_SUBFEATURE_VID:
|
||||
i = nr + MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES * 6;
|
||||
i = nr + MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES *
|
||||
MAX_SENSOR_TYPES * 2;
|
||||
break;
|
||||
case SENSORS_SUBFEATURE_BEEP_ENABLE:
|
||||
i = MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES * 6 +
|
||||
MAX_SENSORS_PER_TYPE;
|
||||
i = MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES *
|
||||
MAX_SENSOR_TYPES * 2 + MAX_SENSORS_PER_TYPE;
|
||||
break;
|
||||
default:
|
||||
i = (sftype >> 8) * MAX_SENSORS_PER_TYPE *
|
||||
@@ -389,7 +418,8 @@ static int sensors_read_dynamic_chip(sensors_chip_features *chip,
|
||||
if (!all_subfeatures[i].name)
|
||||
continue;
|
||||
|
||||
if (i >= MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES * 6 ||
|
||||
if (i >= MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES *
|
||||
MAX_SENSOR_TYPES * 2 ||
|
||||
i / (MAX_SUBFEATURES * 2) != prev_slot) {
|
||||
fnum++;
|
||||
prev_slot = i / (MAX_SUBFEATURES * 2);
|
||||
@@ -410,7 +440,8 @@ static int sensors_read_dynamic_chip(sensors_chip_features *chip,
|
||||
continue;
|
||||
|
||||
/* New main feature? */
|
||||
if (i >= MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES * 6 ||
|
||||
if (i >= MAX_SENSORS_PER_TYPE * MAX_SUBFEATURES *
|
||||
MAX_SENSOR_TYPES * 2 ||
|
||||
i / (MAX_SUBFEATURES * 2) != prev_slot) {
|
||||
ftype = all_subfeatures[i].type >> 8;
|
||||
fnum++;
|
||||
|
||||
Reference in new issue
Block a user