]> Repositories - Adafruit_Blinka-hackapet.git/blob - src/adafruit_blinka/microcontroller/generic_linux/sysfs_analogin.py
Merge pull request #460 from makermelissa/master
[Adafruit_Blinka-hackapet.git] / src / adafruit_blinka / microcontroller / generic_linux / sysfs_analogin.py
1 """
2 `analogio` - Analog input control
3 =================================================
4 Read the SysFS ADC using IIO (Industrial Input/Output) and return the value
5
6 See `CircuitPython:analogio` in CircuitPython for more details.
7 * Author(s): Melissa LeBlanc-Williams
8 """
9
10 import os
11 from adafruit_blinka import ContextManaged
12
13 try:
14     from microcontroller.pin import analogIns
15 except ImportError:
16     raise RuntimeError("No Analog Inputs defined for this board") from ImportError
17
18
19 class AnalogIn(ContextManaged):
20     """Analog Input Class"""
21
22     # Sysfs paths
23     _sysfs_path = "/sys/bus/iio/devices/"
24     _device_path = "iio:device{}"
25
26     # Channel paths
27     _channel_path = "in_voltage{}_raw"
28     _scale_path = "in_voltage_scale"
29
30     def __init__(self, adc_id):
31         """Instantiate an AnalogIn object and verify the sysfs IIO
32         corresponding to the specified channel and pin.
33
34         Args:
35             adc_id (int): Analog Input ID as defined in microcontroller.pin
36
37         Returns:
38             AnalogIn: AnalogIn object.
39
40         Raises:
41             TypeError: if `channel` or `pin` types are invalid.
42             ValueError: if AnalogIn channel does not exist.
43
44         """
45
46         self.id = adc_id
47         self._device = None
48         self._channel = None
49         self._open(adc_id)
50
51     def __enter__(self):
52         return self
53
54     def _open(self, adc_id):
55         self._device = None
56         for adcpair in analogIns:
57             if adcpair[0] == adc_id:
58                 self._device = adcpair[1]
59                 self._channel = adcpair[2]
60
61         if self._device is None:
62             raise RuntimeError("No AnalogIn device found for the given ID")
63
64         device_path = os.path.join(
65             self._sysfs_path, self._device_path.format(self._device)
66         )
67
68         if not os.path.isdir(device_path):
69             raise ValueError(
70                 "AnalogIn device does not exist, check that the required modules are loaded."
71             )
72
73     @property
74     def value(self):
75         """Read the ADC and return the value as an integer"""
76         path = os.path.join(
77             self._sysfs_path,
78             self._device_path.format(self._device),
79             self._channel_path.format(self._channel),
80         )
81
82         with open(path, "r") as analog_in:
83             return int(analog_in.read().strip())
84
85     # pylint: disable=no-self-use
86     @value.setter
87     def value(self, value):
88         # emulate what CircuitPython does
89         raise AttributeError("'AnalogIn' object has no attribute 'value'")
90
91     # pylint: enable=no-self-use
92
93     def deinit(self):
94         self._device = None
95         self._channel = None