Skip to content

Commit

Permalink
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add support for adis1550 and adis16550w
Browse files Browse the repository at this point in the history
Signed-off-by: rbudai <robert.budai@analog.com>
rbudai98 committed Oct 21, 2024
1 parent 67bba95 commit 3bce801
Showing 3 changed files with 528 additions and 0 deletions.
1 change: 1 addition & 0 deletions adi/__init__.py
Original file line number Diff line number Diff line change
@@ -73,6 +73,7 @@
adis16547,
)
from adi.adis16507 import adis16507
from adi.adis16550 import adis16550
from adi.adl5240 import adl5240
from adi.adl5960 import adl5960
from adi.admv8818 import admv8818
464 changes: 464 additions & 0 deletions adi/adis16550.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,464 @@
# Copyright (C) 2019-2024 Analog Devices, Inc.
#
# SPDX short identifier: ADIBSD

from abc import ABC, abstractmethod

from adi.attribute import attribute
from adi.context_manager import context_manager
from adi.rx_tx import rx


class adis16550(rx, context_manager, ABC):

_complex_data = False

_rx_channel_names = [
"anglvel_x",
"anglvel_y",
"anglvel_z",
"accel_x",
"accel_y",
"accel_z",
"temp0",
]

_device_name = ""

"""Disable mapping of trigger to RX device."""
disable_trigger = False

# @property
@abstractmethod
def compatible_parts(self):
raise NotImplementedError

def __init__(self, uri="", device_name=None, trigger_name=None):
context_manager.__init__(self, uri, self._device_name)

if not device_name:
device_name = self.compatible_parts[0]

if device_name not in self.compatible_parts:
raise Exception(
"Not a compatible device:"
+ str(device_name)
+ ".Please select from:"
+ str(self.compatible_parts)
)
else:
self._ctrl = self._ctx.find_device(device_name)
self._rxadc = self._ctx.find_device(device_name)
if not trigger_name:
trigger_name = device_name + "-dev0"

if self._ctrl is None:
print(
"No device found with device_name = "
+ device_name
+ ". Searching for a device found in the compatible list."
)
for i in self.compatible_parts:
self._ctrl = self._ctx.find_device(i)
self._rxadc = self._ctx.find_device(i)
if self._ctrl is not None:
print("Fond device = " + i + ". Will use this device instead.")
break
if self._ctrl is None:
raise Exception("No compatible device found")

self.anglvel_x = self._anglvel_accel_channels(self._ctrl, "anglvel_x")
self.anglvel_y = self._anglvel_accel_channels(self._ctrl, "anglvel_y")
self.anglvel_z = self._anglvel_accel_channels(self._ctrl, "anglvel_z")
self.accel_x = self._anglvel_accel_channels(self._ctrl, "accel_x")
self.accel_y = self._anglvel_accel_channels(self._ctrl, "accel_y")
self.accel_z = self._anglvel_accel_channels(self._ctrl, "accel_z")
self.temp = self._temp_channel(self._ctrl, "temp0")
self.deltaangl_x = self._delta_channels(self._ctrl, "deltaangl_x")
self.deltaangl_y = self._delta_channels(self._ctrl, "deltaangl_y")
self.deltaangl_z = self._delta_channels(self._ctrl, "deltaangl_z")
self.deltavelocity_x = self._delta_channels(self._ctrl, "deltavelocity_x")
self.deltavelocity_y = self._delta_channels(self._ctrl, "deltavelocity_y")
self.deltavelocity_z = self._delta_channels(self._ctrl, "deltavelocity_z")

# Set default trigger
if not self.disable_trigger:
self._trigger = self._ctx.find_device(trigger_name)
self._rxadc._set_trigger(self._trigger)

rx.__init__(self)
self.rx_buffer_size = 16 # Make default buffer smaller

def __get_scaled_sensor(self, channel_name: str) -> float:
raw = self._get_iio_attr(channel_name, "raw", False)
scale = self._get_iio_attr(channel_name, "scale", False)

return raw * scale

def __get_scaled_sensor_temp(self, channel_name: str) -> float:
raw = self._get_iio_attr(channel_name, "raw", False)
scale = self._get_iio_attr(channel_name, "scale", False)
offset = self._get_iio_attr(channel_name, "offset", False)

return (raw + offset) * scale

def get_anglvel_x(self):
"""Value returned in radians per second."""
return self.__get_scaled_sensor("anglvel_x")

anglvel_x_conv = property(get_anglvel_x, None)

def get_anglvel_y(self):
"""Value returned in radians per second."""
return self.__get_scaled_sensor("anglvel_y")

anglvel_y_conv = property(get_anglvel_y, None)

def get_anglvel_z(self):
"""Value returned in radians per second."""
return self.__get_scaled_sensor("anglvel_z")

anglvel_z_conv = property(get_anglvel_z, None)

def get_accel_x(self):
"""Value returned in meters per squared second."""
return self.__get_scaled_sensor("accel_x")

accel_x_conv = property(get_accel_x, None)

def get_accel_y(self):
"""Value returned in meters per squared second."""
return self.__get_scaled_sensor("accel_y")

accel_y_conv = property(get_accel_y, None)

def get_accel_z(self):
"""Value returned in meters per squared second."""
return self.__get_scaled_sensor("accel_z")

accel_z_conv = property(get_accel_z, None)

def get_temp(self):
"""Value returned in millidegrees Celsius."""
return self.__get_scaled_sensor_temp("temp0")

temp_conv = property(get_temp, None)

def get_deltaangl_x(self):
"""Value returned in radians."""
return self.__get_scaled_sensor("deltaangl_x")

deltaangl_x_conv = property(get_deltaangl_x, None)

def get_deltaangl_y(self):
"""Value returned in radians."""
return self.__get_scaled_sensor("deltaangl_y")

deltaangl_y_conv = property(get_deltaangl_y, None)

def get_deltaangl_z(self):
"""Value returned in radians."""
return self.__get_scaled_sensor("deltaangl_z")

deltaangl_z_conv = property(get_deltaangl_z, None)

def get_deltavelocity_x(self):
"""Value returned in meters per second."""
return self.__get_scaled_sensor("deltavelocity_x")

deltavelocity_x_conv = property(get_deltavelocity_x, None)

def get_deltavelocity_y(self):
"""Value returned in meters per second."""
return self.__get_scaled_sensor("deltavelocity_y")

deltavelocity_y_conv = property(get_deltavelocity_y, None)

def get_deltavelocity_z(self):
"""Value returned in meters per second."""
return self.__get_scaled_sensor("deltavelocity_z")

deltavelocity_z_conv = property(get_deltavelocity_z, None)

@property
def sample_rate(self):
"""sample_rate: Sample rate in samples per second"""
return self._get_iio_dev_attr("sampling_frequency")

@sample_rate.setter
def sample_rate(self, value):
self._set_iio_dev_attr_str("sampling_frequency", value)

@property
def current_timestamp_clock(self):
"""current_timestamp_clock: Source clock for timestamps"""
return self._get_iio_dev_attr("current_timestamp_clock")

@current_timestamp_clock.setter
def current_timestamp_clock(self, value):
self._set_iio_dev_attr_str("current_timestamp_clock", value)

@property
def anglvel_x_calibbias(self):
"""User calibration offset for gyroscope for the x-axis."""
return self._get_iio_attr("anglvel_x", "calibbias", False)

@anglvel_x_calibbias.setter
def anglvel_x_calibbias(self, value):
self._set_iio_attr("anglvel_x", "calibbias", False, value)

@property
def anglvel_y_calibbias(self):
"""User calibration offset for gyroscope for the y-axis."""
return self._get_iio_attr("anglvel_y", "calibbias", False)

@anglvel_y_calibbias.setter
def anglvel_y_calibbias(self, value):
self._set_iio_attr("anglvel_y", "calibbias", False, value)

@property
def anglvel_z_calibbias(self):
"""User calibration offset for gyroscope for the z-axis."""
return self._get_iio_attr("anglvel_z", "calibbias", False)

@anglvel_z_calibbias.setter
def anglvel_z_calibbias(self, value):
self._set_iio_attr("anglvel_z", "calibbias", False, value)

@property
def accel_x_calibbias(self):
"""User calibration offset for accelerometer for the x-axis."""
return self._get_iio_attr("accel_x", "calibbias", False)

@accel_x_calibbias.setter
def accel_x_calibbias(self, value):
self._set_iio_attr("accel_x", "calibbias", False, value)

@property
def accel_y_calibbias(self):
"""User calibration offset for accelerometer for the y-axis."""
return self._get_iio_attr("accel_y", "calibbias", False)

@accel_y_calibbias.setter
def accel_y_calibbias(self, value):
self._set_iio_attr("accel_y", "calibbias", False, value)

@property
def accel_z_calibbias(self):
"""User calibration offset for accelerometer for the z-axis."""
return self._get_iio_attr("accel_z", "calibbias", False)

@accel_z_calibbias.setter
def accel_z_calibbias(self, value):
self._set_iio_attr("accel_z", "calibbias", False, value)

@property
def anglvel_x_calibscale(self):
"""Calibscale value for gyroscope for the x-axis."""
return self._get_iio_attr("anglvel_x", "calibscale", False)

@anglvel_x_calibscale.setter
def anglvel_x_calibscale(self, value):
self._set_iio_attr("anglvel_x", "calibscale", False, value)

@property
def anglvel_y_calibscale(self):
"""Calibscale value for gyroscope for the y-axis."""
return self._get_iio_attr("anglvel_y", "calibscale", False)

@anglvel_y_calibscale.setter
def anglvel_y_calibscale(self, value):
self._set_iio_attr("anglvel_y", "calibscale", False, value)

@property
def anglvel_z_calibscale(self):
"""Calibscale value for gyroscope for the z-axis."""
return self._get_iio_attr("anglvel_z", "calibscale", False)

@anglvel_z_calibscale.setter
def anglvel_z_calibscale(self, value):
self._set_iio_attr("anglvel_z", "calibscale", False, value)

@property
def accel_x_calibscale(self):
"""Calibscale value for accelerometer for the x-axis."""
return self._get_iio_attr("accel_x", "calibscale", False)

@accel_x_calibscale.setter
def accel_x_calibscale(self, value):
self._set_iio_attr("accel_x", "calibscale", False, value)

@property
def accel_y_calibscale(self):
"""Calibcale value for accelerometer for the y-axis."""
return self._get_iio_attr("accel_y", "calibscale", False)

@accel_y_calibscale.setter
def accel_y_calibscale(self, value):
self._set_iio_attr("accel_y", "calibscale", False, value)

@property
def accel_z_calibscale(self):
"""Calibscale for accelerometer for the z-axis."""
return self._get_iio_attr("accel_z", "calibscale", False)

@accel_z_calibscale.setter
def accel_z_calibscale(self, value):
self._set_iio_attr("accel_z", "calibscale", False, value)

@property
def anglvel_x_filter_low_pass_3db_frequency(self):
"""Bandwidth for gyroscope for the x-axis."""
return self._get_iio_attr("anglvel_x", "filter_low_pass_3db_frequency", False)

@anglvel_x_filter_low_pass_3db_frequency.setter
def anglvel_x_filter_low_pass_3db_frequency(self, value):
self._set_iio_attr("anglvel_x", "filter_low_pass_3db_frequency", False, value)

@property
def anglvel_y_filter_low_pass_3db_frequency(self):
"""Bandwidth for gyroscope for the y-axis."""
return self._get_iio_attr("anglvel_y", "filter_low_pass_3db_frequency", False)

@anglvel_y_filter_low_pass_3db_frequency.setter
def anglvel_y_filter_low_pass_3db_frequency(self, value):
self._set_iio_attr("anglvel_y", "filter_low_pass_3db_frequency", False, value)

@property
def anglvel_z_filter_low_pass_3db_frequency(self):
"""Bandwidth for gyroscope for the z-axis."""
return self._get_iio_attr("anglvel_z", "filter_low_pass_3db_frequency", False)

@anglvel_z_filter_low_pass_3db_frequency.setter
def anglvel_z_filter_low_pass_3db_frequency(self, value):
self._set_iio_attr("anglvel_z", "filter_low_pass_3db_frequency", False, value)

@property
def accel_x_filter_low_pass_3db_frequency(self):
"""Bandwidth for accelerometer for the x-axis."""
return self._get_iio_attr("accel_x", "filter_low_pass_3db_frequency", False)

@accel_x_filter_low_pass_3db_frequency.setter
def accel_x_filter_low_pass_3db_frequency(self, value):
self._set_iio_attr("accel_x", "filter_low_pass_3db_frequency", False, value)

@property
def accel_y_filter_low_pass_3db_frequency(self):
"""Bandwidth for accelerometer for the y-axis."""
return self._get_iio_attr("accel_y", "filter_low_pass_3db_frequency", False)

@accel_y_filter_low_pass_3db_frequency.setter
def accel_y_filter_low_pass_3db_frequency(self, value):
self._set_iio_attr("accel_y", "filter_low_pass_3db_frequency", False, value)

@property
def accel_z_filter_low_pass_3db_frequency(self):
"""Bandwidth for accelerometer for the z-axis."""
return self._get_iio_attr("accel_z", "filter_low_pass_3db_frequency", False)

@accel_z_filter_low_pass_3db_frequency.setter
def accel_z_filter_low_pass_3db_frequency(self, value):
self._set_iio_attr("accel_z", "filter_low_pass_3db_frequency", False, value)

class _temp_channel(attribute):
"""ADIS16550 temperature channel."""

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

@property
def raw(self):
"""ADIS16550 raw value"""
return self._get_iio_attr(self.name, "raw", False)

@property
def scale(self):
"""ADIS16550 scale value"""
return self._get_iio_attr(self.name, "scale", False)

@property
def offset(self):
"""ADIS16550 offset value"""
return self._get_iio_attr(self.name, "offset", False)

class _simple_channel(attribute):
"""ADIS16550 basic channel, only scale an raw values"""

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

@property
def raw(self):
"""ADIS16550 raw value"""
return self._get_iio_attr(self.name, "raw", False)

@property
def scale(self):
"""ADIS16550 scale value"""
return self._get_iio_attr(self.name, "scale", False)

class _extended_channel(_simple_channel):
"""ADIS16550 pressure channel."""

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

@property
def calibbias(self):
"""ADIS16550 calibration offset"""
return self._get_iio_attr(self.name, "calibbias", False)

@calibbias.setter
def calibbias(self, value):
self._set_iio_attr(self.name, "calibbias", False, value)

@property
def calibscale(self):
"""ADIS16550 calibration scale"""
return self._get_iio_attr(self.name, "calibscale", False)

@calibscale.setter
def calibscale(self, value):
self._set_iio_attr(self.name, "calibscale", False, value)

@property
def filter_low_pass_3db_frequency(self):
"""ADIS16550 channel bandwidth"""
return self._get_iio_attr(self.name, "filter_low_pass_3db_frequency", False)

@filter_low_pass_3db_frequency.setter
def filter_low_pass_3db_frequency(self, value):
self._set_iio_attr(self.name, "filter_low_pass_3db_frequency", False, value)

class _anglvel_accel_channels(_extended_channel):
"""ADIS16550 gyro and accelerometer channels."""

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

class _delta_channels(_simple_channel):
"""ADIS16550 delta angle and delta velocity channels."""

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


class adis16550(adis16550):
"""ADIS1655X Six Degrees of Freedom Inertial Sensor
This class is compatible with the following parts:
- ADIS16550
- ADIS16550W
Args:
uri: URI of IIO context with ADIS16550 device
device_name: Name of the device in the IIO context. Default is adis16550
trigger_name: Name of the trigger in the IIO context. Default is adis16550-dev0
"""

compatible_parts = ["adis16550", "adis16550w"]
63 changes: 63 additions & 0 deletions examples/adis16550_example.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
# Copyright (C) 2024 Analog Devices, Inc.
#
# SPDX short identifier: ADIBSD
import sys

import adi
import matplotlib.pyplot as plt

# Set up ADIS16550
my_dev_name = sys.argv[1]
my_uri = sys.argv[2]

dev = adi.adis16550(device_name=my_dev_name, uri=my_uri)

dev.rx_output_type = "raw"
dev.rx_enabled_channels = [0, 1, 2, 3, 4, 5]
dev.sample_rate = 10
dev.rx_buffer_size = 10

print("Product id: " + str(dev.product_id))
print("Serial number: " + dev.serial_number)
print("Firmware revision: " + dev.firmware_revision)
print("Firmware date: " + dev.firmware_date)

print("\nX acceleration: " + str(dev.accel_x_conv) + " m/s^2")
print("Y acceleration: " + str(dev.accel_y_conv) + " m/s^2")
print("Z acceleration: " + str(dev.accel_z_conv) + " m/s^2")

print("\nX angular velocity: " + str(dev.anglvel_x_conv) + " rad/s")
print("Y angular velocity: " + str(dev.anglvel_y_conv) + " rad/s")
print("Z angular velocity: " + str(dev.anglvel_z_conv) + " rad/s")

print("\nX delta velocity: " + str(dev.deltavelocity_x_conv) + " m/s")
print("Y delta velocity: " + str(dev.deltavelocity_y_conv) + " m/s")
print("Z delta velocity: " + str(dev.deltavelocity_z_conv) + " m/s")

print("\nX delta angle: " + str(dev.deltaangl_x_conv) + " rad")
print("Y delta angle: " + str(dev.deltaangl_y_conv) + " rad")
print("Z delta angle: " + str(dev.deltaangl_z_conv) + " rad")

dev.sample_rate = 2000
dev.magn_x_filter_low_pass_3db_frequency = 100
dev.anglvel_y_calibscale = 30
dev.anglvel_x_calibbias = 100

print("\nSampling frequency: " + str(dev.sample_rate))

print("Temperature raw value: " + str(dev.temp.raw))
print("Temperature scale value: " + str(dev.temp.scale))
print("Temperature offset value: " + str(dev.temp.offset))

print("X-axis gyro channel calibbias value: " + str(dev.anglvel_x_calibbias))
print("X-axis gyro channel calibscale value: " + str(dev.anglvel_y_calibscale))
print("X-axis magnetometer bandwidth: " + str(dev.magn_x_filter_low_pass_3db_frequency))

for _ in range(100):
data = dev.rx()
plt.clf()
for i, d in enumerate(data):
plt.plot(d, label=dev._rx_channel_names[dev.rx_enabled_channels[i]])
plt.legend()
plt.show(block=False)
plt.pause(0.1)

0 comments on commit 3bce801

Please sign in to comment.