OLD | NEW |
(Empty) | |
| 1 # Copyright 2017 The Chromium Authors. All rights reserved. |
| 2 # Use of this source code is governed by a BSD-style license that can be |
| 3 # found in the LICENSE file. |
| 4 import collections |
| 5 import re |
| 6 |
| 7 # Named tuple for all monsoon samples. |
| 8 MonsoonSample = collections.namedtuple('MonsoonSample', 'Timestamp Amps') |
| 9 |
| 10 # Regular expression to extract timestamp and amperage from Monsoon's log. |
| 11 SampleRegex = re.compile(r"(\d+)\s+(?<![a-zA-Z:])([-+]?\d*\.?\d+)") |
| 12 |
| 13 def ReadSamplesFromFile(file): |
| 14 """ Reads raw samples from a file in the form 'Timestamp Amps', returning |
| 15 a list of MonsoonSample tuples. |
| 16 """ |
| 17 samples = [] |
| 18 for line in file: |
| 19 value_match = SampleRegex.match(line) |
| 20 # Sometimes there can be transient USB communication errors. They can be |
| 21 # safely ignored. |
| 22 if value_match is not None: |
| 23 # Some versions of monsoon.py supply timestamp in integer. Some later |
| 24 # versions could in theory supply timestamp as a float. Collapse all |
| 25 # and treat timestamps as if they were integer seconds. |
| 26 timestamp_second = int(value_match.group(1)) |
| 27 amps = float(value_match.group(2)) |
| 28 samples.append(MonsoonSample(Timestamp = timestamp_second, Amps = amps)) |
| 29 return samples |
| 30 |
| 31 def TransformSamplesWithFrequency(samples, frequency): |
| 32 """ Transforms a list of MonsoonSample (with integer second accuracy) into a |
| 33 list of MonsoonSample with fractional accuracy, assuming a fixed frequency. |
| 34 """ |
| 35 result = [] |
| 36 second_samples = [] |
| 37 second = -1 |
| 38 last_index = len(samples) - 1 |
| 39 for i,source_sample in enumerate(samples): |
| 40 if second == -1: |
| 41 second = source_sample.Timestamp |
| 42 if (source_sample.Timestamp != second) or (i == last_index): |
| 43 # Now and then the data may have more samples than the given frequency |
| 44 # (a desktop OS isn't an RTOS after all). Lets allow it and average out |
| 45 # the samples. |
| 46 if len(second_samples) > frequency: |
| 47 second_frequency = len(second_samples) |
| 48 else: |
| 49 second_frequency = frequency |
| 50 period = 1.0 / second_frequency |
| 51 # Samples are represented as halfway through the period. |
| 52 time_offset = -(period / 2.0) |
| 53 if len(result) == 0: |
| 54 time_offset += (second_frequency - len(second_samples) - 1) * period |
| 55 for second_sample in second_samples: |
| 56 result.append(MonsoonSample(Timestamp = second + time_offset, Amps = |
| 57 second_sample.Amps)) |
| 58 time_offset += period |
| 59 del second_samples[:] |
| 60 second = source_sample.Timestamp |
| 61 second_samples.append(source_sample) |
| 62 return result |
OLD | NEW |