1
0
mirror of https://github.com/ARM-software/workload-automation.git synced 2024-10-06 19:01:15 +01:00
workload-automation/wlauto/instrumentation/hwmon/__init__.py
Sergei Trofimov 7a86a1b17f hwmon: move sensor discovery into initialize()
It only needs to be done once per run.
2015-05-07 09:39:33 +01:00

123 lines
4.5 KiB
Python

# Copyright 2013-2015 ARM Limited
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# pylint: disable=W0613,E1101
from __future__ import division
from collections import OrderedDict
from wlauto import Parameter, Instrument
from wlauto.exceptions import InstrumentError, ConfigError
from wlauto.utils.hwmon import discover_sensors
from wlauto.utils.types import list_of_strs
# sensor_kind: (report_type, units, conversion)
HWMON_SENSORS = {
'energy': ('diff', 'Joules', lambda x: x / 10 ** 6),
'temp': ('before/after', 'Celsius', lambda x: x / 10 ** 3),
}
HWMON_SENSOR_PRIORITIES = ['energy', 'temp']
class HwmonInstrument(Instrument):
name = 'hwmon'
description = """
Hardware Monitor (hwmon) is a generic Linux kernel subsystem,
providing access to hardware monitoring components like temperature or
voltage/current sensors.
The following web page has more information:
http://blogs.arm.com/software-enablement/925-linux-hwmon-power-management-and-arm-ds-5-streamline/
You can specify which sensors HwmonInstrument looks for by specifying
hwmon_sensors in your config.py, e.g. ::
hwmon_sensors = ['energy', 'temp']
If this setting is not specified, it will look for all sensors it knows about.
Current valid values are::
:energy: Collect energy measurements and report energy consumed
during run execution (the diff of before and after readings)
in Joules.
:temp: Collect temperature measurements and report the before and
after readings in degrees Celsius.
"""
parameters = [
Parameter('sensors', kind=list_of_strs, default=['energy', 'temp'],
description='The kinds of sensors hwmon instrument will look for')
]
def __init__(self, device, **kwargs):
super(HwmonInstrument, self).__init__(device, **kwargs)
if self.sensors:
self.sensor_kinds = {}
for kind in self.sensors:
if kind in HWMON_SENSORS:
self.sensor_kinds[kind] = HWMON_SENSORS[kind]
else:
message = 'Unexpected sensor type: {}; must be in {}'.format(kind, HWMON_SENSORS.keys())
raise ConfigError(message)
else:
self.sensor_kinds = HWMON_SENSORS
self.sensors = []
def initialize(self, context):
self.sensors = []
self.logger.debug('Searching for HWMON sensors.')
discovered_sensors = discover_sensors(self.device, self.sensor_kinds.keys())
for sensor in sorted(discovered_sensors, key=lambda s: HWMON_SENSOR_PRIORITIES.index(s.kind)):
self.logger.debug('Adding {}'.format(sensor.filepath))
self.sensors.append(sensor)
def setup(self, context):
for sensor in self.sensors:
sensor.clear_readings()
def fast_start(self, context):
for sensor in reversed(self.sensors):
sensor.take_reading()
def fast_stop(self, context):
for sensor in self.sensors:
sensor.take_reading()
def update_result(self, context):
for sensor in self.sensors:
try:
report_type, units, conversion = HWMON_SENSORS[sensor.kind]
if report_type == 'diff':
before, after = sensor.readings
diff = conversion(after - before)
context.result.add_metric(sensor.label, diff, units)
elif report_type == 'before/after':
before, after = sensor.readings
context.result.add_metric(sensor.label + ' before', conversion(before), units)
context.result.add_metric(sensor.label + ' after', conversion(after), units)
else:
raise InstrumentError('Unexpected report_type: {}'.format(report_type))
except ValueError, e:
self.logger.error('Could not collect all {} readings for {}'.format(sensor.kind, sensor.label))
self.logger.error('Got: {}'.format(e))