Index: leahi_dialin/dd/modules/post_gen_dialysate.py =================================================================== diff -u --- leahi_dialin/dd/modules/post_gen_dialysate.py (revision 0) +++ leahi_dialin/dd/modules/post_gen_dialysate.py (revision 80f84ad5638667894e9df2161b9c5d9b8f27ed9b) @@ -0,0 +1,64 @@ +########################################################################### +# +# Copyright (c) 2020-2024 Diality Inc. - All Rights Reserved. +# +# THIS CODE MAY NOT BE COPIED OR REPRODUCED IN ANY FORM, IN PART OR IN +# WHOLE, WITHOUT THE EXPLICIT PERMISSION OF THE COPYRIGHT OWNER. +# +# @file post_gen_dialysate.py +# +# @author (last) Micahel Garthwaite +# @date (last) 07-Mar-2023 +# @author (original) Micahel Garthwaite +# @date (original) 29-Oct-2020 +# +############################################################################ +import struct +from enum import unique +from logging import Logger + +from .constants import RESET, NO_RESET +from leahi_dialin.common.msg_defs import MsgIds, MsgFieldPositions +from leahi_dialin.protocols.CAN import DenaliMessage, DenaliChannels +from leahi_dialin.utils.base import AbstractSubSystem, publish, DialinEnum +from leahi_dialin.utils.checks import check_broadcast_interval_override_ms +from leahi_dialin.utils.conversions import integer_to_bytearray, float_to_bytearray + +class DDGenDialysate(AbstractSubSystem): + """ + Gen Dialysate + + Dialysate Delivery (DD) Dialin API sub-class for gen dialysate related commands. + """ + + def __init__(self, can_interface, logger: Logger): + """ + + @param can_interface: Denali Can Messenger object + """ + super().__init__() + + self.can_interface = can_interface + self.logger = logger + + if self.can_interface is not None: + channel_id = DenaliChannels.dd_sync_broadcast_ch_id + msg_id = MsgIds.MSG_ID_DD_POST_GEN_DIALYSATE_STATE_DATA.value + self.can_interface.register_receiving_publication_function(channel_id, msg_id, + self._handler_post_gen_dialysate_sync) + + self.execution_state = 0 + self.post_gen_state_timestamp = 0 + + def _handler_post_gen_dialysate_sync(self, message, timestamp=0.0): + """ + Handles published gen dialysate data messages. + + @param message: published gen dialysate data message + @return: None + """ + + self.execution_state = struct.unpack('I', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_1:MsgFieldPositions.END_POS_FIELD_1]))[0] + + post_gen_state_timestamp = timestamp \ No newline at end of file Index: leahi_dialin/dd/modules/pre_gen_dialysate.py =================================================================== diff -u --- leahi_dialin/dd/modules/pre_gen_dialysate.py (revision 0) +++ leahi_dialin/dd/modules/pre_gen_dialysate.py (revision 80f84ad5638667894e9df2161b9c5d9b8f27ed9b) @@ -0,0 +1,69 @@ +########################################################################### +# +# Copyright (c) 2020-2024 Diality Inc. - All Rights Reserved. +# +# THIS CODE MAY NOT BE COPIED OR REPRODUCED IN ANY FORM, IN PART OR IN +# WHOLE, WITHOUT THE EXPLICIT PERMISSION OF THE COPYRIGHT OWNER. +# +# @file pre_gen_dialysate.py +# +# @author (last) Micahel Garthwaite +# @date (last) 07-Mar-2023 +# @author (original) Micahel Garthwaite +# @date (original) 29-Oct-2020 +# +############################################################################ +import struct +from enum import unique +from logging import Logger + +from .constants import RESET, NO_RESET +from leahi_dialin.common.msg_defs import MsgIds, MsgFieldPositions +from leahi_dialin.protocols.CAN import DenaliMessage, DenaliChannels +from leahi_dialin.utils.base import AbstractSubSystem, publish, DialinEnum +from leahi_dialin.utils.checks import check_broadcast_interval_override_ms +from leahi_dialin.utils.conversions import integer_to_bytearray, float_to_bytearray + +class DDGenDialysate(AbstractSubSystem): + """ + Gen Dialysate + + Dialysate Delivery (DD) Dialin API sub-class for gen dialysate related commands. + """ + + def __init__(self, can_interface, logger: Logger): + """ + + @param can_interface: Denali Can Messenger object + """ + super().__init__() + + self.can_interface = can_interface + self.logger = logger + + if self.can_interface is not None: + channel_id = DenaliChannels.dd_sync_broadcast_ch_id + msg_id = MsgIds.MSG_ID_DD_PRE_GEN_DIALYSATE_STATE_DATA.value + self.can_interface.register_receiving_publication_function(channel_id, msg_id, + self._handler_pre_gen_state_sync) + + channel_id = DenaliChannels.dd_sync_broadcast_ch_id + msg_id = MsgIds.MSG_ID_DD_PRE_GEN_DIALYSATE_REQUEST_DATA.value + self.can_interface.register_receiving_publication_function(channel_id, msg_id, + self._handler_pre_gen_request_sync) + + self.execution_state = 0 + self.pre_gen_state_timestamp = 0 + + def _handler_pre_gen_state_sync(self, message, timestamp=0.0): + """ + Handles published gen dialysate data messages. + + @param message: published gen dialysate data message + @return: None + """ + + self.execution_state = struct.unpack('I', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_1:MsgFieldPositions.END_POS_FIELD_1]))[0] + + pre_gen_state_timestamp = timestamp \ No newline at end of file Index: leahi_dialin/dd/modules/temperature_sensors.py =================================================================== diff -u -r71216b08590dd4b556c10b3384dddc26c8d29a99 -r80f84ad5638667894e9df2161b9c5d9b8f27ed9b --- leahi_dialin/dd/modules/temperature_sensors.py (.../temperature_sensors.py) (revision 71216b08590dd4b556c10b3384dddc26c8d29a99) +++ leahi_dialin/dd/modules/temperature_sensors.py (.../temperature_sensors.py) (revision 80f84ad5638667894e9df2161b9c5d9b8f27ed9b) @@ -33,10 +33,6 @@ D50_TEMP = 3 # Trimmer heater temperature sensor BARO_TEMP = 4 # Barometric temperature sensor BRD_TEMP = 5 # DD board temperature sensor ( thermistor ) - D16_TEMP = 6 # Bicarb only conductivity sensor temp - D28_TEMP = 7 # Acid and Bicarb mix conductivity sensor - 1 temp - D30_TEMP = 8 # Acid and Bicarb mix conductivity sensor - 2 temp - D44_TEMP = 9 # Spent dialysate conductivity sensor temp class DDTemperatureSensors(AbstractSubSystem): @@ -54,11 +50,7 @@ DDTemperaturesNames.D4_TEMP.name: 0.0, DDTemperaturesNames.D50_TEMP.name: 0.0, DDTemperaturesNames.BARO_TEMP.name: 0.0, - DDTemperaturesNames.BRD_TEMP.name: 0.0, - DDTemperaturesNames.D16_TEMP.name: 0.0, - DDTemperaturesNames.D28_TEMP.name: 0.0, - DDTemperaturesNames.D30_TEMP.name: 0.0, - DDTemperaturesNames.D44_TEMP.name: 0.0,} + DDTemperaturesNames.BRD_TEMP.name: 0.0,} if self.can_interface is not None: channel_id = DenaliChannels.dd_sync_broadcast_ch_id @@ -92,18 +84,6 @@ self.dd_temperatures[DDTemperaturesNames.BRD_TEMP.name] = struct.unpack('f', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_6:MsgFieldPositions.END_POS_FIELD_6]))[0] - self.dd_temperatures[DDTemperaturesNames.D16_TEMP.name] = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_7:MsgFieldPositions.END_POS_FIELD_7]))[0] - - self.dd_temperatures[DDTemperaturesNames.D28_TEMP.name] = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_8:MsgFieldPositions.END_POS_FIELD_8]))[0] - - self.dd_temperatures[DDTemperaturesNames.D30_TEMP.name] = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_9:MsgFieldPositions.END_POS_FIELD_9]))[0] - - self.dd_temperatures[DDTemperaturesNames.D44_TEMP.name] = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_10:MsgFieldPositions.END_POS_FIELD_10]))[0] - self.dd_temperatures_timestamp = timestamp def cmd_temperatures_data_broadcast_interval_override(self, ms: int, reset: int = NO_RESET) -> int: Index: leahi_dialin/fp/modules/boost_pump.py =================================================================== diff -u -r0f08c28544b557b2bbd8c04b10cff284f41e4fb9 -r80f84ad5638667894e9df2161b9c5d9b8f27ed9b --- leahi_dialin/fp/modules/boost_pump.py (.../boost_pump.py) (revision 0f08c28544b557b2bbd8c04b10cff284f41e4fb9) +++ leahi_dialin/fp/modules/boost_pump.py (.../boost_pump.py) (revision 80f84ad5638667894e9df2161b9c5d9b8f27ed9b) @@ -49,19 +49,19 @@ self.can_interface.register_receiving_publication_function(channel_id, msg_id, self._handler_boost_pump_sync) self.ro_pump_timestamp = 0.0 - self.p12_ro_pump_state = 0 - self.p12_ro_pump_duty_cycle = 0.0 - self.p12_ro_pump_fb_duty_cycle = 0.0 - self.p12_ro_pump_speed = 0.0 - self.p40_boost_pump_state = 0 - self.p40_boost_pump_duty_cycle = 0.0 - self.p40_boost_pump_fb_duty_cycle = 0.0 - self.p40_boost_pump_speed = 0.0 + self.p12_pump_state = 0 + self.p12_pump_duty_cycle = 0.0 + self.p12_pump_fb_duty_cycle = 0.0 + self.p12_pump_speed = 0.0 + self.p40_pump_state = 0 + self.p40_pump_duty_cycle = 0.0 + self.p40_pump_fb_duty_cycle = 0.0 + self.p40_pump_speed = 0.0 - @publish(["ro_pump_timestamp", "p12_ro_pump_state", "p12_ro_pump_duty_cycle", "p12_ro_pump_fb_duty_cycle", - "p12_ro_pump_speed", "p40_boost_pump_state", "p40_boost_pump_duty_cycle", - "p40_boost_pump_fb_duty_cycle", "p40_boost_pump_speed"]) + @publish(["ro_pump_timestamp", "p12_pump_state", "p12_pump_duty_cycle", "p12_pump_fb_duty_cycle", + "p12_pump_speed", "p40_pump_state", "p40_pump_duty_cycle", + "p40_pump_fb_duty_cycle", "p40_pump_speed"]) def _handler_boost_pump_sync(self, message, timestamp=0.0): """ Handles published RO pump data messages. RO pump data is captured @@ -71,35 +71,25 @@ @return: none """ - rps = struct.unpack('i', bytearray( + self.p12_pump_state = struct.unpack('i', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_1:MsgFieldPositions.END_POS_FIELD_1])) - rpdc = struct.unpack('i', bytearray( + self.p12_pump_duty_cycle = struct.unpack('i', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_2:MsgFieldPositions.END_POS_FIELD_2])) - rpfbdc = struct.unpack('i', bytearray( + self.p12_pump_fb_duty_cycle = struct.unpack('i', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_3:MsgFieldPositions.END_POS_FIELD_3])) - rprpm = struct.unpack('f', bytearray( + self.p12_pump_speed = struct.unpack('f', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_4:MsgFieldPositions.END_POS_FIELD_4])) - bps = struct.unpack('i', bytearray( + self.p40_pump_state = struct.unpack('i', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_5:MsgFieldPositions.END_POS_FIELD_5])) - bpdc = struct.unpack('i', bytearray( + self.p40_pump_duty_cycle = struct.unpack('i', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_6:MsgFieldPositions.END_POS_FIELD_6])) - bpfbdc = struct.unpack('i', bytearray( + self.p40_pump_fb_duty_cycle = struct.unpack('i', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_7:MsgFieldPositions.END_POS_FIELD_7])) - bprpm = struct.unpack('f', bytearray( + self.p40_pump_speed = struct.unpack('f', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_8:MsgFieldPositions.END_POS_FIELD_8])) self.ro_pump_timestamp = timestamp - self.p12_ro_pump_state = rps[0] - self.p12_ro_pump_duty_cycle = rpdc[0] - self.p12_ro_pump_fb_duty_cycle = rpfbdc[0] - self.p12_ro_pump_speed = rprpm[0] - self.p40_boost_pump_state = bps[0] - self.p40_boost_pump_duty_cycle = bpdc[0] - self.p40_boost_pump_fb_duty_cycle = bpfbdc[0] - self.p40_boost_pump_speed = bprpm[0] - - def cmd_boost_pump_set_speed_rate_override(self, pump: int, rpm: int, reset: int = NO_RESET) -> int: """ Constructs and sends the boost pump set point command @@ -144,8 +134,8 @@ Constraints: Must be logged into FP. + @param pump: integer - the pump id to set pwm @param pwm: integer - counts to override the pwm ( 0 - 500 ) - @param reset: integer - 1 to reset a previous override, 0 to override @return: 1 if successful, zero otherwise """ Index: leahi_dialin/fp/modules/pressure_sensors.py =================================================================== diff -u -r5b9473d9ca6a66d4d03c509fae6051710895b498 -r80f84ad5638667894e9df2161b9c5d9b8f27ed9b --- leahi_dialin/fp/modules/pressure_sensors.py (.../pressure_sensors.py) (revision 5b9473d9ca6a66d4d03c509fae6051710895b498) +++ leahi_dialin/fp/modules/pressure_sensors.py (.../pressure_sensors.py) (revision 80f84ad5638667894e9df2161b9c5d9b8f27ed9b) @@ -33,6 +33,10 @@ P13_PRES = 3 P17_PRES = 4 X1_PRES = 5 + X2_PRES = 6 + X3_PRES = 7 + X4_PRES = 8 + X5_PRES = 9 class FPPressureSensors(AbstractSubSystem): @@ -62,28 +66,26 @@ self.p13_pres = 0.0 self.p17_pres = 0.0 self.x1_pres = 0.0 + self.x2_pres = 0.0 + self.x3_pres = 0.0 + self.x4_pres = 0.0 + self.x5_pres = 0.0 self.m1_pres_temp = 0.0 self.m3_pres_temp = 0.0 self.p8_pres_temp = 0.0 self.p13_pres_temp = 0.0 self.p17_pres_temp = 0.0 self.x1_pres_temp = 0.0 + self.x2_pres_temp = 0.0 + self.x3_pres_temp = 0.0 + self.x4_pres_temp = 0.0 + self.x5_pres_temp = 0.0 - @publish([ - "fp_pressure_timestamp", - "m1_pres", - "m3_pres", - "p8_pres", - "p13_pres", - "p17_pres", - "x1_pres", - "m1_pres_temp", - "m3_pres_temp", - "p8_pres_temp", - "p13_pres_temp", - "p17_pres_temp", - "x1_pres_temp" + "fp_pressure_timestamp", "m1_pres", "m3_pres", "p8_pres", "p13_pres", "p17_pres", + "x1_pres", "x2_pres", "x3_pres", "x4_pres", "x5_pres", + "m1_pres_temp", "m3_pres_temp", "p8_pres_temp", "p13_pres_temp", "p17_pres_temp", + "x1_pres_temp", "x2_pres_temp", "x3_pres_temp", "x4_pres_temp", "x5_pres_temp", ]) def _handler_pressure_sync(self, message, timestamp=0.0): """ @@ -94,46 +96,48 @@ @return: none """ - pre_reg_wi = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_1:MsgFieldPositions.END_POS_FIELD_1])) - post_reg_wi = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_2:MsgFieldPositions.END_POS_FIELD_2])) - pre_cond_wi = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_3:MsgFieldPositions.END_POS_FIELD_3])) - pre_ro = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_4:MsgFieldPositions.END_POS_FIELD_4])) - post_ro = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_5:MsgFieldPositions.END_POS_FIELD_5])) - pre_pump = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_6:MsgFieldPositions.END_POS_FIELD_6])) + self.m1_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_1:MsgFieldPositions.END_POS_FIELD_1]))[0] + self.m3_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_2:MsgFieldPositions.END_POS_FIELD_2]))[0] + self.p8_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_3:MsgFieldPositions.END_POS_FIELD_3]))[0] + self.p13_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_4:MsgFieldPositions.END_POS_FIELD_4]))[0] + self.p17_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_5:MsgFieldPositions.END_POS_FIELD_5]))[0] + self.x1_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_6:MsgFieldPositions.END_POS_FIELD_6]))[0] + self.x2_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_7:MsgFieldPositions.END_POS_FIELD_7]))[0] + self.x3_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_8:MsgFieldPositions.END_POS_FIELD_8]))[0] + self.x4_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_9:MsgFieldPositions.END_POS_FIELD_9]))[0] + self.x5_pres = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_10:MsgFieldPositions.END_POS_FIELD_10]))[0] - pre_reg_wi_temp = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_7:MsgFieldPositions.END_POS_FIELD_7])) - post_reg_wi_temp = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_8:MsgFieldPositions.END_POS_FIELD_8])) - pre_cond_wi_temp = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_9:MsgFieldPositions.END_POS_FIELD_9])) - pre_ro_temp = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_10:MsgFieldPositions.END_POS_FIELD_10])) - post_ro_temp = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_11:MsgFieldPositions.END_POS_FIELD_11])) - pre_pump_temp = struct.unpack('f', bytearray( - message['message'][MsgFieldPositions.START_POS_FIELD_12:MsgFieldPositions.END_POS_FIELD_12])) + self.m1_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_11:MsgFieldPositions.END_POS_FIELD_11]))[0] + self.m3_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_12:MsgFieldPositions.END_POS_FIELD_12]))[0] + self.p8_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_13:MsgFieldPositions.END_POS_FIELD_13]))[0] + self.p13_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_14:MsgFieldPositions.END_POS_FIELD_14]))[0] + self.p17_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_15:MsgFieldPositions.END_POS_FIELD_15]))[0] + self.x1_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_16:MsgFieldPositions.END_POS_FIELD_16]))[0] + self.x2_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_17:MsgFieldPositions.END_POS_FIELD_17]))[0] + self.x3_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_18:MsgFieldPositions.END_POS_FIELD_18]))[0] + self.x4_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_19:MsgFieldPositions.END_POS_FIELD_19]))[0] + self.x5_pres_temp = struct.unpack('f', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_20:MsgFieldPositions.END_POS_FIELD_20]))[0] - self.m1_pres = pre_reg_wi[0] - self.m3_pres = post_reg_wi[0] - self.p8_pres = pre_cond_wi[0] - self.p13_pres = pre_ro[0] - self.p17_pres = post_ro[0] - self.x1_pres = pre_pump[0] - - self.m1_pres_temp = pre_reg_wi_temp[0] - self.m3_pres_temp = post_reg_wi_temp[0] - self.p8_pres_temp = pre_cond_wi_temp[0] - self.p13_pres_temp = pre_ro_temp[0] - self.p17_pres_temp = post_ro_temp[0] - self.x1_pres_temp = pre_pump_temp[0] - self.fp_pressure_timestamp = timestamp def cmd_pressure_sensor_override(self, sensor: int, pressure: float, reset: int = NO_RESET) -> int: