Skip to content

Commit

Permalink
Merge pull request #522 from analogdevicesinc/ltc2664-dev
Browse files Browse the repository at this point in the history
iio: dac: ltc2664: Device class for LTC2664 4 channel DAC
  • Loading branch information
tfcollins authored Apr 9, 2024
2 parents a17a959 + f34b02a commit ddb3ec3
Show file tree
Hide file tree
Showing 9 changed files with 260 additions and 0 deletions.
1 change: 1 addition & 0 deletions adi/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,7 @@
from adi.ltc2314_14 import ltc2314_14
from adi.ltc2387 import ltc2387
from adi.ltc2499 import ltc2499
from adi.ltc2664 import ltc2664
from adi.ltc2688 import ltc2688
from adi.ltc2983 import ltc2983
from adi.max9611 import max9611
Expand Down
166 changes: 166 additions & 0 deletions adi/ltc2664.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,166 @@
# Copyright (C) 2024 Analog Devices, Inc.
#
# SPDX short identifier: ADIBSD

from adi.attribute import attribute
from adi.context_manager import context_manager


class ltc2664(context_manager, attribute):
""" LTC2664 DAC """

_complex_data = False
_device_name = "LTC2664"
channel_names = []

def __init__(self, uri="ip:analog.local", device_index=0):
context_manager.__init__(self, uri, self._device_name)

self._ctrl = self._ctx.find_device("ltc2664")

for ch in self._ctrl.channels:
name = ch.id
self.channel_names.append(name)
if "toggle_en" in ch.attrs:
setattr(self, name, self._channel_toggle(self._ctrl, name))
else:
setattr(self, name, self._channel_standard(self._ctrl, name))

class _channel_base(attribute):
""" LTC2664 base channel class """

def __init__(self, ctrl, channel_name):
self.name = channel_name
self._ctrl = ctrl

@property
def scale(self):
""" LTC2664 channel gain """
return self._get_iio_attr(self.name, "scale", True, self._ctrl)

@property
def offset(self):
""" LTC2664 channel offset """
return self._get_iio_attr(self.name, "offset", True, self._ctrl)

@property
def volt_available(self):
""" LTC2664 voltage min/max [min, max] in mV """
return [
round((0 + self.offset) * self.scale, 2),
round((65535 + self.offset) * self.scale, 2),
]

@property
def raw_available(self):
""" LTC2664 raw value range [min, increment, max] """
return list(
map(
int,
(self._get_iio_attr(self.name, "raw_available", True, self._ctrl)),
)
)

@property
def powerdown(self):
""" LTC2664 channel powerdown """
return self._get_iio_attr(self.name, "powerdown", True, self._ctrl)

@powerdown.setter
def powerdown(self, val):
""" LTC2664 channel powerdown """
self._set_iio_attr(self.name, "powerdown", True, val, self._ctrl)

class _channel_standard(_channel_base):
def __init__(self, ctrl, channel_name):
super().__init__(ctrl, channel_name)

@property
def raw(self):
""" LTC2664 channel raw value property """
return self._get_iio_attr(self.name, "raw", True, self._ctrl)

@raw.setter
def raw(self, val):
""" LTC2664 channel raw value setter """
raw_span = self._get_iio_attr(self.name, "raw_available", True, self._ctrl)
if val >= raw_span[0] and val <= raw_span[2] and val % raw_span[1] == 0:
self._set_iio_attr(self.name, "raw", True, str(int(val)))

@property
def volt(self):
""" LTC2664 channel volt property (in mV)"""
return (self.raw + self.offset) * self.scale

@volt.setter
def volt(self, val):
""" LTC2664 channel volt setter (in mV)"""
self.raw = int((val / self.scale) - self.offset)

class _channel_toggle(_channel_base):
def __init__(self, ctrl, channel_name):
super().__init__(ctrl, channel_name)

@property
def toggle_en(self):
""" LTC2664 channel toggle enable flag """
return self._get_iio_attr(self.name, "toggle_en", True, self._ctrl)

@toggle_en.setter
def toggle_en(self, val):
""" LTC2664 channel toggle enable flag setter """
self._set_iio_attr(self.name, "toggle_en", True, val)

@property
def toggle_state(self):
""" LTC2664 SW toggle enable flag """
return self._get_iio_attr(self.name, "symbol", True, self._ctrl)

@toggle_state.setter
def toggle_state(self, val):
""" LTC2664 SW toggle enable flag setter """
self._set_iio_attr(self.name, "symbol", True, str(int(val)))

@property
def raw0(self):
""" LTC2664 channel toggle state 0 raw value """
return self._get_iio_attr(self.name, "raw0", True, self._ctrl)

@raw0.setter
def raw0(self, val):
""" LTC2664 channel toggle state 0 raw value setter """
raw_span = self._get_iio_attr(self.name, "raw_available", True, self._ctrl)
if val >= raw_span[0] and val <= raw_span[2] and val % raw_span[1] == 0:
self._set_iio_attr(self.name, "raw0", True, str(int(val)))

@property
def raw1(self):
""" LTC2664 channel toggle state 1 raw value """
return self._get_iio_attr(self.name, "raw1", True, self._ctrl)

@raw1.setter
def raw1(self, val):
""" LTC2664 channel toggle state 1 raw value setter """
raw_span = self._get_iio_attr(self.name, "raw_available", True, self._ctrl)
if val >= raw_span[0] and val <= raw_span[2] and val % raw_span[1] == 0:
self._set_iio_attr(self.name, "raw1", True, str(int(val)))

@property
def volt0(self):
""" LTC2664 channel toggle state 0 voltage value (in mV)"""
return (self.raw0 + self.offset) * self.scale

@volt0.setter
def volt0(self, val):
""" LTC2664 channel toggle state 0 voltage value setter (in mV)"""
self.raw0 = int(((val / self.scale) - self.offset))

@property
def volt1(self):
""" LTC2664 channel toggle state 1 voltage value (in mV)"""
return (self.raw1 + self.offset) * self.scale

@volt1.setter
def volt1(self, val):
""" LTC2664 channel toggle state 1 voltage value setter (in mV)"""
self.raw1 = int(((val / self.scale) - self.offset))
7 changes: 7 additions & 0 deletions doc/source/devices/adi.ltc2664.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
ltc2664
==================

.. automodule:: adi.ltc2664
:members:
:undoc-members:
:show-inheritance:
1 change: 1 addition & 0 deletions doc/source/devices/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,7 @@ Supported Devices
adi.ltc2314_14
adi.ltc2387
adi.ltc2499
adi.ltc2664
adi.ltc2688
adi.ltc2983
adi.max11205
Expand Down
40 changes: 40 additions & 0 deletions examples/ltc2664_example.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
# Copyright (C) 2023 Analog Devices, Inc.
#
# SPDX short identifier: ADIBSD

import sys
import time

import adi

# Device initialization
try:
myDAC = adi.ltc2664(uri="ip:analog.local")

for ch in myDAC.channel_names:
ch_object = eval("myDAC." + str(ch))
voltage_range = ch_object.volt_available
raw_value_range = ch_object.raw_available
print(
"LTC2644 channel "
+ ch
+ " configured output range "
+ str(voltage_range)
+ " mV: RAW value range "
+ str(raw_value_range)
)

except Exception as e:
print(str(e))
print("Failed to open LTC2664 device")
sys.exit(0)

# sweep entire output range in 100mV steps
voltage_range = myDAC.voltage0.volt_available

for v in range(int(voltage_range[0]), int(voltage_range[1]), 100):
print("setting voltage0 = " + str(v / 1000) + " Volt")
myDAC.voltage0.volt = v
time.sleep(0.05)

myDAC.voltage0.powerdown = 1
1 change: 1 addition & 0 deletions supported_parts.md
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,7 @@
- LTC2314-14
- LTC2387-18
- LTC2499
- LTC2664
- LTC2688
- LTC2983
- AD7606
Expand Down
1 change: 1 addition & 0 deletions test/emu/devices/ltc2664.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<?xml version="1.0" encoding="utf-8"?><!DOCTYPE context [<!ELEMENT context (device | context-attribute)*><!ELEMENT context-attribute EMPTY><!ELEMENT device (channel | attribute | debug-attribute | buffer-attribute)*><!ELEMENT channel (scan-element?, attribute*)><!ELEMENT attribute EMPTY><!ELEMENT scan-element EMPTY><!ELEMENT debug-attribute EMPTY><!ELEMENT buffer-attribute EMPTY><!ATTLIST context name CDATA #REQUIRED description CDATA #IMPLIED><!ATTLIST context-attribute name CDATA #REQUIRED value CDATA #REQUIRED><!ATTLIST device id CDATA #REQUIRED name CDATA #IMPLIED><!ATTLIST channel id CDATA #REQUIRED type (input|output) #REQUIRED name CDATA #IMPLIED><!ATTLIST scan-element index CDATA #REQUIRED format CDATA #REQUIRED scale CDATA #IMPLIED><!ATTLIST attribute name CDATA #REQUIRED filename CDATA #IMPLIED value CDATA #IMPLIED><!ATTLIST debug-attribute name CDATA #REQUIRED value CDATA #IMPLIED><!ATTLIST buffer-attribute name CDATA #REQUIRED value CDATA #IMPLIED>]><context name="network" description="10.44.3.92 Linux analog 6.1.54-v7l+ #3472 SMP Thu Jan 25 16:22:37 CET 2024 armv7l" ><context-attribute name="hw_carrier" value="Raspberry Pi 4 Model B Rev 1.4" /><context-attribute name="dtoverlay" value="rpi-ltc2664,vc4-kms-v3d" /><context-attribute name="hw_model" value="0x0001 on Raspberry Pi 4 Model B Rev 1.4" /><context-attribute name="hw_mezzanine" value="0x0001" /><context-attribute name="hw_name" value="PMD-RPI-INTZ" /><context-attribute name="hw_vendor" value="Analog Devices, Inc." /><context-attribute name="hw_serial" value="13837e96-186d-45af-ac0b-e252c8d49a78" /><context-attribute name="local,kernel" value="6.1.54-v7l+" /><context-attribute name="uri" value="ip:analog.local" /><context-attribute name="ip,ip-addr" value="10.44.3.92" /><device id="hwmon0" name="rpi_volt" ><channel id="in0" type="input" ><attribute name="lcrit_alarm" filename="in0_lcrit_alarm" value="0" /></channel></device><device id="iio:device0" name="ltc2664" ><channel id="voltage2" type="output" ><attribute name="offset" filename="out_voltage2_offset" value="-32768" /><attribute name="powerdown" filename="out_voltage2_powerdown" value="0" /><attribute name="raw" filename="out_voltage2_raw" value="0" /><attribute name="raw_available" filename="out_voltage2_raw_available" value="[0 1 65535]" /><attribute name="scale" filename="out_voltage2_scale" value="0.305175781" /></channel><channel id="voltage0" type="output" ><attribute name="offset" filename="out_voltage0_offset" value="-32768" /><attribute name="powerdown" filename="out_voltage0_powerdown" value="1" /><attribute name="raw" filename="out_voltage0_raw" value="65208" /><attribute name="raw_available" filename="out_voltage0_raw_available" value="[0 1 65535]" /><attribute name="scale" filename="out_voltage0_scale" value="0.305175781" /></channel><channel id="voltage3" type="output" ><attribute name="offset" filename="out_voltage3_offset" value="-32768" /><attribute name="powerdown" filename="out_voltage3_powerdown" value="0" /><attribute name="raw" filename="out_voltage3_raw" value="16000" /><attribute name="raw_available" filename="out_voltage3_raw_available" value="[0 1 65535]" /><attribute name="scale" filename="out_voltage3_scale" value="0.305175781" /></channel><channel id="voltage1" type="output" ><attribute name="offset" filename="out_voltage1_offset" value="-32768" /><attribute name="powerdown" filename="out_voltage1_powerdown" value="0" /><attribute name="raw0" filename="out_voltage1_raw0" value="0" /><attribute name="raw1" filename="out_voltage1_raw1" value="0" /><attribute name="raw_available" filename="out_voltage1_raw_available" value="[0 1 65535]" /><attribute name="scale" filename="out_voltage1_scale" value="0.305175781" /><attribute name="symbol" filename="out_voltage1_symbol" value="0" /><attribute name="toggle_en" filename="out_voltage1_toggle_en" value="0" /></channel><attribute name="waiting_for_supplier" value="0" /><debug-attribute name="direct_reg_access" value="ERROR" /></device></context>
9 changes: 9 additions & 0 deletions test/emu/hardware_map.yml
Original file line number Diff line number Diff line change
Expand Up @@ -403,6 +403,15 @@ ltc2387:
- filename: ltc2387.xml
- data_devices:
- iio:device0
ltc2664:
- ltc2664
- pyadi_iio_class_support:
- ltc2664
- emulate:
- filename: ltc2664.xml
- data_devices:
- iio:device0

ltc2688:
- ltc2688
- pyadi_iio_class_support:
Expand Down
34 changes: 34 additions & 0 deletions test/test_ltc2664.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import pytest

hardware = "ltc2664"
classname = "adi.ltc2664"


#########################################
@pytest.mark.iio_hardware(hardware)
@pytest.mark.parametrize("classname", [(classname)])
@pytest.mark.parametrize(
"attr, start, stop, step, tol, repeats, sub_channel",
[
("raw", 0, 65000, 1000, 1, 3, "voltage0"), # Standard Channel
("raw0", 0, 65000, 1000, 1, 3, "voltage1"), # Toggle Channel
("raw1", 0, 65000, 1000, 1, 3, "voltage1"), # Toggle Channel
("raw", 0, 65000, 1000, 1, 3, "voltage2"), # Standard Channel
("raw", 0, 65000, 1000, 1, 3, "voltage3"), # Standard Channel
],
)
def test_ltc2688_raw_attr(
test_attribute_single_value,
iio_uri,
classname,
attr,
start,
stop,
step,
tol,
repeats,
sub_channel,
):
test_attribute_single_value(
iio_uri, classname, attr, start, stop, step, tol, repeats, sub_channel
)

0 comments on commit ddb3ec3

Please sign in to comment.