blob: 8aee1ce528ac0cbf97bbb57e0c6a87bfb86f9d2c [file] [log] [blame]
Sergei Trofimov4e6afe92015-10-09 09:30:04 +01001Instrumentation
2===============
3
4The ``Instrument`` API provide a consistent way of collecting measurements from
5a target. Measurements are collected via an instance of a class derived from
6:class:`Instrument`. An ``Instrument`` allows collection of measurement from one
7or more channels. An ``Instrument`` may support ``INSTANTANEOUS`` or
8``CONTINUOUS`` collection, or both.
9
10Example
11-------
12
13The following example shows how to use an instrument to read temperature from an
14Android target.
15
16.. code-block:: ipython
17
18 # import and instantiate the Target and the instrument
19 # (note: this assumes exactly one android target connected
20 # to the host machine).
21 In [1]: from devlib import AndroidTarget, HwmonInstrument
22
23 In [2]: t = AndroidTarget()
24
25 In [3]: i = HwmonInstrument(t)
26
27 # Set up the instrument on the Target. In case of HWMON, this is
28 # a no-op, but is included here for completeness.
29 In [4]: i.setup()
30
Brendan Jackmanfc814772017-04-26 15:07:33 +010031 # Find out what the instrument is capable collecting from the
Sergei Trofimov4e6afe92015-10-09 09:30:04 +010032 # target.
33 In [5]: i.list_channels()
34 Out[5]:
35 [CHAN(battery/temp1, battery_temperature),
36 CHAN(exynos-therm/temp1, exynos-therm_temperature)]
37
38 # Set up a new measurement session, and specify what is to be
39 # collected.
40 In [6]: i.reset(sites=['exynos-therm'])
41
42 # HWMON instrument supports INSTANTANEOUS collection, so invoking
Brendan Jackmanfc814772017-04-26 15:07:33 +010043 # take_measurement() will return a list of measurements take from
Sergei Trofimov4e6afe92015-10-09 09:30:04 +010044 # each of the channels configured during reset()
45 In [7]: i.take_measurement()
46 Out[7]: [exynos-therm_temperature: 36.0 degrees]
47
48API
49---
50
51Instrument
52~~~~~~~~~~
53
54.. class:: Instrument(target, **kwargs)
55
56 An ``Instrument`` allows collection of measurement from one or more
57 channels. An ``Instrument`` may support ``INSTANTANEOUS`` or ``CONTINUOUS``
58 collection, or both.
59
60.. attribute:: Instrument.mode
61
62 A bit mask that indicates collection modes that are supported by this
63 instrument. Possible values are:
64
65 :INSTANTANEOUS: The instrument supports taking a single sample via
66 ``take_measurement()``.
67 :CONTINUOUS: The instrument supports collecting measurements over a
68 period of time via ``start()``, ``stop()``, and
69 ``get_data()`` methods.
70
Brendan Jackmanfc814772017-04-26 15:07:33 +010071 .. note:: It's possible for one instrument to support more than a single
Sergei Trofimov4e6afe92015-10-09 09:30:04 +010072 mode.
73
74.. attribute:: Instrument.active_channels
75
76 Channels that have been activated via ``reset()``. Measurements will only be
77 collected for these channels.
78
79.. method:: Instrument.list_channels()
80
81 Returns a list of :class:`InstrumentChannel` instances that describe what
82 this instrument can measure on the current target. A channel is a combination
83 of a ``kind`` of measurement (power, temperature, etc) and a ``site`` that
84 indicates where on the target the measurement will be collected from.
85
86.. method:: Instrument.get_channels(measure)
87
88 Returns channels for a particular ``measure`` type. A ``measure`` can be
89 either a string (e.g. ``"power"``) or a :class:`MeasurmentType` instance.
90
91.. method:: Instrument.setup(*args, **kwargs)
92
93 This will set up the instrument on the target. Parameters this method takes
94 are particular to subclasses (see documentation for specific instruments
95 below). What actions are performed by this method are also
96 instrument-specific. Usually these will be things like installing
97 executables, starting services, deploying assets, etc. Typically, this method
98 needs to be invoked at most once per reboot of the target (unless
99 ``teardown()`` has been called), but see documentation for the instrument
100 you're interested in.
101
Brendan Jackman1513db02017-05-10 11:18:21 +0100102.. method:: Instrument.reset(sites=None, kinds=None, channels=None)
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100103
104 This is used to configure an instrument for collection. This must be invoked
Brendan Jackman1513db02017-05-10 11:18:21 +0100105 before ``start()`` is called to begin collection. This methods sets the
106 ``active_channels`` attribute of the ``Instrument``.
107
108 If ``channels`` is provided, it is a list of names of channels to enable and
109 ``sites`` and ``kinds`` must both be ``None``.
110
111 Otherwise, if one of ``sites`` or ``kinds`` is provided, all channels
112 matching the given sites or kinds are enabled. If both are provided then all
113 channels of the given kinds at the given sites are enabled.
114
115 If none of ``sites``, ``kinds`` or ``channels`` are provided then all
116 available channels are enabled.
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100117
118.. method:: Instrument.take_measurment()
119
120 Take a single measurement from ``active_channels``. Returns a list of
121 :class:`Measurement` objects (one for each active channel).
122
123 .. note:: This method is only implemented by :class:`Instrument`\ s that
Marc Bonnici1fd56362017-01-10 15:35:21 +0000124 support ``INSTANTANEOUS`` measurement.
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100125
126.. method:: Instrument.start()
127
128 Starts collecting measurements from ``active_channels``.
129
130 .. note:: This method is only implemented by :class:`Instrument`\ s that
Marc Bonnici1fd56362017-01-10 15:35:21 +0000131 support ``CONTINUOUS`` measurement.
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100132
133.. method:: Instrument.stop()
134
135 Stops collecting measurements from ``active_channels``. Must be called after
136 :func:`start()`.
137
138 .. note:: This method is only implemented by :class:`Instrument`\ s that
Marc Bonnici1fd56362017-01-10 15:35:21 +0000139 support ``CONTINUOUS`` measurement.
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100140
141.. method:: Instrument.get_data(outfile)
142
Brendan Jackmanfc814772017-04-26 15:07:33 +0100143 Write collected data into ``outfile``. Must be called after :func:`stop()`.
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100144 Data will be written in CSV format with a column for each channel and a row
Brendan Jackmanfc814772017-04-26 15:07:33 +0100145 for each sample. Column heading will be channel, labels in the form
Marc Bonnici1fd56362017-01-10 15:35:21 +0000146 ``<site>_<kind>`` (see :class:`InstrumentChannel`). The order of the columns
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100147 will be the same as the order of channels in ``Instrument.active_channels``.
148
Marc Bonnicic62905c2017-08-18 17:22:47 +0100149 If reporting timestamps, one channel must have a ``site`` named ``"timestamp"``
150 and a ``kind`` of a :class:`MeasurmentType` of an appropriate time unit which will
151 be used, if appropriate, during any post processing.
152
153 .. note:: Currently supported time units are seconds, milliseconds and
154 microseconds, other units can also be used if an appropriate
155 conversion is provided.
156
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100157 This returns a :class:`MeasurementCsv` instance associated with the outfile
158 that can be used to stream :class:`Measurement`\ s lists (similar to what is
159 returned by ``take_measurement()``.
160
161 .. note:: This method is only implemented by :class:`Instrument`\ s that
Marc Bonnici1fd56362017-01-10 15:35:21 +0000162 support ``CONTINUOUS`` measurement.
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100163
Brendan Jackman49b547a2017-04-26 15:07:05 +0100164.. attribute:: Instrument.sample_rate_hz
165
166 Sample rate of the instrument in Hz. Assumed to be the same for all channels.
167
168 .. note:: This attribute is only provided by :class:`Instrument`\ s that
Marc Bonnicieeb5e932017-08-07 15:39:38 +0100169 support ``CONTINUOUS`` measurement.
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100170
171Instrument Channel
172~~~~~~~~~~~~~~~~~~
173
174.. class:: InstrumentChannel(name, site, measurement_type, **attrs)
175
176 An :class:`InstrumentChannel` describes a single type of measurement that may
177 be collected by an :class:`Instrument`. A channel is primarily defined by a
178 ``site`` and a ``measurement_type``.
179
180 A ``site`` indicates where on the target a measurement is collected from
Marc Bonnici1fd56362017-01-10 15:35:21 +0000181 (e.g. a voltage rail or location of a sensor).
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100182
183 A ``measurement_type`` is an instance of :class:`MeasurmentType` that
Marc Bonnici1fd56362017-01-10 15:35:21 +0000184 describes what sort of measurement this is (power, temperature, etc). Each
185 measurement type has a standard unit it is reported in, regardless of an
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100186 instrument used to collect it.
187
188 A channel (i.e. site/measurement_type combination) is unique per instrument,
189 however there may be more than one channel associated with one site (e.g. for
Marc Bonnici1fd56362017-01-10 15:35:21 +0000190 both voltage and power).
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100191
192 It should not be assumed that any site/measurement_type combination is valid.
193 The list of available channels can queried with
194 :func:`Instrument.list_channels()`.
195
196.. attribute:: InstrumentChannel.site
197
Marc Bonnici1fd56362017-01-10 15:35:21 +0000198 The name of the "site" from which the measurements are collected (e.g. voltage
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100199 rail, sensor, etc).
200
201.. attribute:: InstrumentChannel.kind
202
Marc Bonnici1fd56362017-01-10 15:35:21 +0000203 A string indicating the type of measurement that will be collected. This is
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100204 the ``name`` of the :class:`MeasurmentType` associated with this channel.
205
206.. attribute:: InstrumentChannel.units
207
Marc Bonnici1fd56362017-01-10 15:35:21 +0000208 Units in which measurement will be reported. this is determined by the
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100209 underlying :class:`MeasurmentType`.
210
211.. attribute:: InstrumentChannel.label
212
Marc Bonnici1fd56362017-01-10 15:35:21 +0000213 A label that can be attached to measurements associated with with channel.
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100214 This is constructed with ::
215
216 '{}_{}'.format(self.site, self.kind)
217
218
219Measurement Types
220~~~~~~~~~~~~~~~~~
221
222In order to make instruments easer to use, and to make it easier to swap them
223out when necessary (e.g. change method of collecting power), a number of
224standard measurement types are defined. This way, for example, power will always
225be reported as "power" in Watts, and never as "pwr" in milliWatts. Currently
226defined measurement types are
227
228
Marc Bonnicic62905c2017-08-18 17:22:47 +0100229+-------------+-------------+---------------+
230| name | units | category |
231+=============+=============+===============+
232| time | seconds | |
233+-------------+-------------+---------------+
234| time | microseconds| |
235+-------------+-------------+---------------+
236| time | milliseconds| |
237+-------------+-------------+---------------+
238| temperature | degrees | |
239+-------------+-------------+---------------+
240| power | watts | power/energy |
241+-------------+-------------+---------------+
242| voltage | volts | power/energy |
243+-------------+-------------+---------------+
244| current | amps | power/energy |
245+-------------+-------------+---------------+
246| energy | joules | power/energy |
247+-------------+-------------+---------------+
248| tx | bytes | data transfer |
249+-------------+-------------+---------------+
250| rx | bytes | data transfer |
251+-------------+-------------+---------------+
252| tx/rx | bytes | data transfer |
253+-------------+-------------+---------------+
Sergei Trofimov4e6afe92015-10-09 09:30:04 +0100254
255
256.. instruments:
257
258Available Instruments
259---------------------
260
261This section lists instruments that are currently part of devlib.
262
263TODO