Index: dialin/common/hd_defs.py =================================================================== diff -u -r965b384855cf17d6b975f9989f13a26248e2d919 -r19ed99efea69f85cf5ea175a39555dfaa8e493e0 --- dialin/common/hd_defs.py (.../hd_defs.py) (revision 965b384855cf17d6b975f9989f13a26248e2d919) +++ dialin/common/hd_defs.py (.../hd_defs.py) (revision 19ed99efea69f85cf5ea175a39555dfaa8e493e0) @@ -1,16 +1,16 @@ -################################################################ +########################################################################### # -# Copyright (c) 2019-2020 Diality Inc. - All Rights Reserved. +# Copyright (c) 2019-2021 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 alarm_defs.py +# @file hd_defs.py # -# @author (last) Peter Lucia -# @date (last) 30-Nov-2020 -# @author (original) Peter Lucia -# @date (original) 30-Nov-2020 +# @author (last) Quang Nguyen +# @date (last) 22-Jul-2021 +# @author (original) Peter Lucia +# @date (original) 04-Dec-2020 # ############################################################################ from enum import unique Index: dialin/common/msg_ids.py =================================================================== diff -u -r89df6a25e4845ad234c1ffc71fb484b73d125b4c -r19ed99efea69f85cf5ea175a39555dfaa8e493e0 --- dialin/common/msg_ids.py (.../msg_ids.py) (revision 89df6a25e4845ad234c1ffc71fb484b73d125b4c) +++ dialin/common/msg_ids.py (.../msg_ids.py) (revision 19ed99efea69f85cf5ea175a39555dfaa8e493e0) @@ -213,8 +213,8 @@ MSG_ID_PRESSURE_ARTERIAL_OVERRIDE = 0X8017 MSG_ID_PRESSURE_VENOUS_OVERRIDE = 0X8018 MSG_ID_OCCLUSION_BLOOD_PUMP_OVERRIDE = 0X8019 - MSG_ID_OCCLUSION_DIAL_IN_PUMP_OVERRIDE = 0X801A - MSG_ID_OCCLUSION_DIAL_OUT_PUMP_OVERRIDE = 0X801B + MSG_ID_BLOOD_PUMP_ROTOR_COUNT_OVERRIDE = 0X801A + MSG_ID_SET_ARTERIAL_PRESSURE_OFFSET = 0X801B MSG_ID_PRES_OCCL_SEND_INTERVAL_OVERRIDE = 0X801C MSG_ID_SET_RTC_DATE_TIME = 0X801D MSG_ID_DIAL_OUT_FLOW_SEND_INTERVAL_OVERRIDE = 0X801E @@ -304,6 +304,9 @@ MSG_ID_HD_PRE_TREATMENT_DATA_PUBLISH_INTERVAL_OVERRIDE = 0x8073 MSG_ID_HD_TREATMENT_DATA_PUBLISH_INTERVAL_OVERRIDE = 0x8074 MSG_ID_HD_POST_TREATMENT_DATA_PUBLISH_INTERVAL_OVERRIDE = 0x8075 + MSG_ID_HD_BLOCK_MESSAGE_TRANSMISSION = 0x8076 + MSG_ID_HD_SYRINGE_PUMP_FORCE_SENSOR_DAC_CALIBRATE = 0x8077 + MSG_ID_DG_TESTER_LOGIN_REQUEST = 0XA000 MSG_ID_DG_ALARM_STATE_OVERRIDE = 0XA001 MSG_ID_DG_WATCHDOG_TASK_CHECKIN_OVERRIDE = 0XA002 @@ -334,7 +337,7 @@ MSG_ID_DG_SWITCHES_STATUS_OVERRIDE = 0XA01D MSG_ID_DG_SWITCHES_PUBLISH_INTERVAL_OVERRIDE = 0XA01E MSG_ID_DG_OP_MODE_PUBLISH_INTERVAL_OVERRIDE = 0XA01F - MSG_ID___AVAILABLE_15 = 0XA020 + MSG_ID_DG_BLOCK_MESSAGE_TRANSMISSION = 0XA020 MSG_ID___AVAILABLE_16 = 0XA021 MSG_ID_DG_SOFTWARE_RESET_REQUEST = 0XA022 MSG_ID_DG_CONCENTRATE_PUMP_MEASURED_SPEED_OVERRIDE = 0XA023 Index: dialin/dg/dialysate_generator.py =================================================================== diff -u -r965b384855cf17d6b975f9989f13a26248e2d919 -r19ed99efea69f85cf5ea175a39555dfaa8e493e0 --- dialin/dg/dialysate_generator.py (.../dialysate_generator.py) (revision 965b384855cf17d6b975f9989f13a26248e2d919) +++ dialin/dg/dialysate_generator.py (.../dialysate_generator.py) (revision 19ed99efea69f85cf5ea175a39555dfaa8e493e0) @@ -1,16 +1,16 @@ ########################################################################### # -# Copyright (c) 2019-2020 Diality Inc. - All Rights Reserved. +# Copyright (c) 2019-2021 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 dialysate_generator.py +# @file dialysate_generator.py # -# @author (last) Peter Lucia -# @date (last) 10-Nov-2020 -# @author (original) Peter Lucia -# @date (original) 02-Apr-2020 +# @author (last) Quang Nguyen +# @date (last) 30-Aug-2021 +# @author (original) Peter Lucia +# @date (original) 02-Apr-2020 # ############################################################################ @@ -45,7 +45,15 @@ from .uv_reactors import UVReactors from .valves import DGValves from .voltages import DGVoltages +from .events import DGEvents from ..common.msg_defs import MsgIds, MsgFieldPositions +from .flush import FlushMode +from .chemical_disinfect import ChemicalDisinfect +from .heat_disinfect import HeatDisinfect +from .rtc import DGRTC +from .switches import DGSwitches +from enum import unique +from .constants import NO_RESET from ..protocols.CAN import DenaliCanMessenger, DenaliMessage, DenaliChannels from ..utils import * from ..utils.base import AbstractSubSystem, publish, LogManager, DialinEnum @@ -180,6 +188,7 @@ self.uv_reactors = UVReactors(self.can_interface, self.logger) self.valves = DGValves(self.can_interface, self.logger) self.voltages = DGVoltages(self.can_interface, self.logger) + self.events = DGEvents(self.can_interface, self.logger) def get_version(self): """ Index: dialin/hd/blood_flow.py =================================================================== diff -u -r8474f8e345f165187d4dde17840575ee4e98a9b4 -r19ed99efea69f85cf5ea175a39555dfaa8e493e0 --- dialin/hd/blood_flow.py (.../blood_flow.py) (revision 8474f8e345f165187d4dde17840575ee4e98a9b4) +++ dialin/hd/blood_flow.py (.../blood_flow.py) (revision 19ed99efea69f85cf5ea175a39555dfaa8e493e0) @@ -51,7 +51,7 @@ self.measured_blood_pump_mc_speed = 0.0 self.measured_blood_pump_mc_current = 0.0 self.pwm_duty_cycle_pct = 0.0 - self.flow_signal_strength = 0.0 + self.rotor_count = 0 def get_target_blood_flow_rate(self): """ @@ -109,13 +109,13 @@ """ return self.pwm_duty_cycle_pct - def get_flow_signal_strength(self): + def get_rotor_count(self): """ - Gets the blood flow signal strength pct + Gets the blood pump rotor count (since cartridge installed) - @return: the blood flow signal strength pct (0..100) + @return: the blood pump rotor count """ - return self.flow_signal_strength + return self.rotor_count @publish(["target_blood_flow_rate", "measured_blood_flow_rate", "measured_blood_pump_rotor_speed", "measured_blood_pump_speed", "measured_blood_pump_mc_speed", "measured_blood_pump_mc_current", @@ -143,7 +143,7 @@ message['message'][MsgFieldPositions.START_POS_FIELD_6:MsgFieldPositions.END_POS_FIELD_6])) pwm = struct.unpack('f', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_7:MsgFieldPositions.END_POS_FIELD_7])) - sig = struct.unpack('f', bytearray( + rot = struct.unpack('i', bytearray( message['message'][MsgFieldPositions.START_POS_FIELD_8:MsgFieldPositions.END_POS_FIELD_8])) self.target_blood_flow_rate = tgt[0] @@ -153,7 +153,7 @@ self.measured_blood_pump_mc_speed = mcspeed[0] self.measured_blood_pump_mc_current = mccurr[0] self.pwm_duty_cycle_pct = pwm[0] - self.flow_signal_strength = sig[0] + self.rotor_count = rot[0] def cmd_blood_flow_set_point_override(self, flow: int, mode: int = PUMP_CONTROL_MODE_CLOSED_LOOP, reset: int = NO_RESET) -> int: @@ -512,3 +512,44 @@ else: self.logger.debug("Timeout!!!!") return False + + def cmd_blood_pump_rotor_count_override(self, rot_count: int, reset: int = NO_RESET) -> int: + """ + Constructs and sends the blood pump rotor count override command + Constraints: + Must be logged into HD. + Given count must be zero or positive integer. + + @param rot_count: integer - rotor count to override with + @param reset: integer - 1 to reset a previous override, 0 to override + @return: 1 if successful, zero otherwise + """ + + rst = integer_to_bytearray(reset) + cnt = integer_to_bytearray(rot_count) + payload = rst + cnt + + message = DenaliMessage.build_message(channel_id=DenaliChannels.dialin_to_hd_ch_id, + message_id=MsgIds.MSG_ID_BLOOD_PUMP_ROTOR_COUNT_OVERRIDE.value, + payload=payload) + + self.logger.debug("override blood pump rotor count") + + # Send message + received_message = self.can_interface.send(message) + + # If there is content... + if received_message is not None: + # self.logger.debug(received_message) + if reset == RESET: + str_res = "reset back to normal: " + else: + str_res = str(rot_count) + ": " + self.logger.debug("Blood pump rotor count overridden to " + str_res + + str(received_message['message'][DenaliMessage.PAYLOAD_START_INDEX])) + # response payload is OK or not OK + return received_message['message'][DenaliMessage.PAYLOAD_START_INDEX] + else: + self.logger.debug("Timeout!!!!") + return False + Index: dialin/hd/hemodialysis_device.py =================================================================== diff -u -r965b384855cf17d6b975f9989f13a26248e2d919 -r19ed99efea69f85cf5ea175a39555dfaa8e493e0 --- dialin/hd/hemodialysis_device.py (.../hemodialysis_device.py) (revision 965b384855cf17d6b975f9989f13a26248e2d919) +++ dialin/hd/hemodialysis_device.py (.../hemodialysis_device.py) (revision 19ed99efea69f85cf5ea175a39555dfaa8e493e0) @@ -1,16 +1,16 @@ ########################################################################### # -# Copyright (c) 2019-2020 Diality Inc. - All Rights Reserved. +# Copyright (c) 2019-2021 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 hemodialysis_device.py +# @file hemodialysis_device.py # -# @author (last) Peter Lucia -# @date (last) 10-Nov-2020 -# @author (original) Peter Lucia -# @date (original) 02-Apr-2020 +# @author (last) Quang Nguyen +# @date (last) 30-Aug-2021 +# @author (original) Peter Lucia +# @date (original) 02-Apr-2020 # ############################################################################ import struct @@ -23,7 +23,6 @@ from .blood_leak import HDBloodLeak from .buttons import HDButtons from .calibration_record import HDCalibrationNVRecord -from .constants import NO_RESET, RESET from .dialysate_inlet_flow import HDDialysateInletFlow from .dialysate_outlet_flow import HDDialysateOutletFlow from .fluid_leak import HDFluidLeak @@ -32,6 +31,9 @@ from .rtc import HDRTC from .service_record import HDServiceNVRecords from .switches import HDSwitches +from .temperatures import HDTemperatures +from .fans import HDFans +from .constants import NO_RESET, RESET from .syringe_pump import HDSyringePump from .system_record import HDSystemNVRecords from .treatment import HDTreatment @@ -117,6 +119,12 @@ self.ui = HDUIProxy(self.can_interface, self.logger) self.valves = HDValves(self.can_interface, self.logger) self.voltages = HDVoltages(self.can_interface, self.logger) + self.calibration_record = HDCalibrationNVRecord(self.can_interface, self.logger) + self.system_record = HDSystemNVRecords(self.can_interface, self.logger) + self.service_record = HDServiceNVRecords(self.can_interface, self.logger) + self.switches = HDSwitches(self.can_interface, self.logger) + self.temperatures = HDTemperatures(self.can_interface, self.logger) + self.fans = HDFans(self.can_interface, self.logger) self.watchdog = HDWatchdog(self.can_interface, self.logger) def get_operation_mode(self): Index: dialin/hd/pressure_occlusion.py =================================================================== diff -u -r8474f8e345f165187d4dde17840575ee4e98a9b4 -r19ed99efea69f85cf5ea175a39555dfaa8e493e0 --- dialin/hd/pressure_occlusion.py (.../pressure_occlusion.py) (revision 8474f8e345f165187d4dde17840575ee4e98a9b4) +++ dialin/hd/pressure_occlusion.py (.../pressure_occlusion.py) (revision 19ed99efea69f85cf5ea175a39555dfaa8e493e0) @@ -356,3 +356,41 @@ else: self.logger.debug("Timeout!!!!") return False + + def cmd_arterial_pressure_offset_override(self, offset: float, reset: int = NO_RESET) -> int: + """ + Constructs and sends the arterial pressure offset override command + Constraints: + Must be logged into HD. + + @param offset: float - offset (in mmHg) for arterial pressure sensor + @param reset: integer - 1 to reset a previous override, 0 to override + @return: 1 if successful, zero otherwise + """ + + rst = integer_to_bytearray(reset) + off = float_to_bytearray(offset) + payload = rst + off + + message = DenaliMessage.build_message(channel_id=DenaliChannels.dialin_to_hd_ch_id, + message_id=MsgIds.MSG_ID_SET_ARTERIAL_PRESSURE_OFFSET.value, + payload=payload) + + self.logger.debug("override arterial pressure offset") + + # Send message + received_message = self.can_interface.send(message) + + # If there is content... + if received_message is not None: + if reset == RESET: + str_res = "reset back to normal: " + else: + str_res = str(offset) + " mmHg: " + self.logger.debug("Arterial pressure offset overridden to " + str_res + + str(received_message['message'][DenaliMessage.PAYLOAD_START_INDEX])) + # response payload is OK or not OK + return received_message['message'][DenaliMessage.PAYLOAD_START_INDEX] + else: + self.logger.debug("Timeout!!!!") + return False Index: dialin/hd/rtc.py =================================================================== diff -u -r076965b54ec7f9711537ad5553de65b4da11338e -r19ed99efea69f85cf5ea175a39555dfaa8e493e0 --- dialin/hd/rtc.py (.../rtc.py) (revision 076965b54ec7f9711537ad5553de65b4da11338e) +++ dialin/hd/rtc.py (.../rtc.py) (revision 19ed99efea69f85cf5ea175a39555dfaa8e493e0) @@ -1,22 +1,23 @@ ########################################################################### # -# Copyright (c) 2019-2020 Diality Inc. - All Rights Reserved. +# Copyright (c) 2019-2021 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 rtc.py +# @file rtc.py # -# @author (last) Peter Lucia -# @date (last) 03-Nov-2020 -# @author (original) Peter Lucia -# @date (original) 02-Apr-2020 +# @author (last) Quang Nguyen +# @date (last) 11-Aug-2021 +# @author (original) Peter Lucia +# @date (original) 02-Apr-2020 # ############################################################################ -import ctypes + +import struct +from ..common.msg_defs import MsgIds, MsgFieldPositions from logging import Logger -from ..common.msg_defs import MsgIds from ..protocols.CAN import DenaliMessage, DenaliChannels from ..utils.base import AbstractSubSystem, publish from ..utils.conversions import integer_to_bytearray @@ -29,9 +30,6 @@ """ - START_POS_SET_PT = DenaliMessage.PAYLOAD_START_INDEX - END_POS_SET_PT = START_POS_SET_PT + 4 - def __init__(self, can_interface, logger: Logger): """ @@ -45,8 +43,7 @@ if self.can_interface is not None: channel_id = DenaliChannels.hd_sync_broadcast_ch_id msg_id = MsgIds.MSG_ID_RTC_EPOCH.value - self.can_interface.register_receiving_publication_function(channel_id, msg_id, - self._handler_rtc_epoch) + self.can_interface.register_receiving_publication_function(channel_id, msg_id, self._handler_rtc_epoch) self.rtc_epoch = 0 def get_rtc_epoch(self): @@ -65,10 +62,9 @@ @param message: published rtc epoch message @return: None """ - epoch = int.from_bytes(bytearray( - message['message'][self.START_POS_SET_PT:self.END_POS_SET_PT]), - byteorder=DenaliMessage.BYTE_ORDER) - self.rtc_epoch = ctypes.c_uint32(epoch) + epoch = struct.unpack('i', bytearray( + message['message'][MsgFieldPositions.START_POS_FIELD_1:MsgFieldPositions.END_POS_FIELD_1]))[0] + self.rtc_epoch = epoch def cmd_set_rtc_time_and_date(self, second: int, minute: int, hour: int, day: int, month: int, year: int) -> int: """ Index: dialin/hd/syringe_pump.py =================================================================== diff -u -r8474f8e345f165187d4dde17840575ee4e98a9b4 -r19ed99efea69f85cf5ea175a39555dfaa8e493e0 --- dialin/hd/syringe_pump.py (.../syringe_pump.py) (revision 8474f8e345f165187d4dde17840575ee4e98a9b4) +++ dialin/hd/syringe_pump.py (.../syringe_pump.py) (revision 19ed99efea69f85cf5ea175a39555dfaa8e493e0) @@ -713,3 +713,35 @@ self.logger.debug("Timeout!!!!") return False + def cmd_set_syringe_pump_dac_ref_voltage(self, dac_v_ref: float = 0.15) -> int: + """ + Constructs and sends the set syringe pump DAC pressure sensor reference voltag command + Constraints: + Must be logged into HD. + + @param dac_v_ref: float - status (0.0..3.3) + @return: 1 if successful, zero otherwise + """ + + payload = float_to_bytearray(dac_v_ref) + + message = DenaliMessage.build_message(channel_id=DenaliChannels.dialin_to_hd_ch_id, + message_id=MsgIds.MSG_ID_HD_SYRINGE_PUMP_FORCE_SENSOR_DAC_CALIBRATE.value, + payload=payload) + + self.logger.debug("set HD syringe pump DAC reference voltage") + + # Send message + received_message = self.can_interface.send(message) + + # If there is content... + if received_message is not None: + str_res = str(dac_v_ref) + self.logger.debug("Syringe pump DAC reference voltage set to " + str_res + "V. " + + str(received_message['message'][DenaliMessage.PAYLOAD_START_INDEX])) + # response payload is OK or not OK + return received_message['message'][DenaliMessage.PAYLOAD_START_INDEX] + else: + self.logger.debug("Timeout!!!!") + return False + Index: dialin/utils/conversions.py =================================================================== diff -u -r965b384855cf17d6b975f9989f13a26248e2d919 -r19ed99efea69f85cf5ea175a39555dfaa8e493e0 --- dialin/utils/conversions.py (.../conversions.py) (revision 965b384855cf17d6b975f9989f13a26248e2d919) +++ dialin/utils/conversions.py (.../conversions.py) (revision 19ed99efea69f85cf5ea175a39555dfaa8e493e0) @@ -1,16 +1,16 @@ ########################################################################### # -# Copyright (c) 2019-2020 Diality Inc. - All Rights Reserved. +# Copyright (c) 2019-2021 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 conversions.py +# @file conversions.py # -# @author (last) Peter Lucia -# @date (last) 06-Oct-2020 -# @author (original) Peter Lucia -# @date (original) 02-Apr-2020 +# @author (last) Quang Nguyen +# @date (last) 07-Jul-2021 +# @author (original) Peter Lucia +# @date (original) 02-Apr-2020 # ############################################################################ import struct