/************************************************************************** * * Copyright (c) 2019-2020 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 ModePostTreat.c * * @author (last) Sean Nash * @date (last) 08-Oct-2020 * * @author (original) Dara Navaei * @date (original) 05-Nov-2019 * ***************************************************************************/ #include "AlarmLamp.h" #include "Buttons.h" #include "BloodFlow.h" #include "DialInFlow.h" #include "DialOutFlow.h" #include "DGInterface.h" #include "FPGA.h" #include "OperationModes.h" #include "ModePostTreat.h" #include "Valves.h" /** * @addtogroup HDPostTreatmentMode * @{ */ // ********** private definitions ********** #define EMPTY_RESERVOIR_VOLUME_ML 0 ///< Empty reservoir volume in ml. #define DIP_FLUSH_FLOW_RATE_ML_MIN 300 ///< Dialysate inlet pump flow rate during flush in mL/min. /// Post-Treatmen de-prime state machine. typedef enum De_Prime_States { DE_PRIME_FIRST_DRAIN_STATE = 0, ///< De-prime drain first reservoir state. DE_PRIME_FLUSH_BYPASS_STATE, ///< De-prime drain second reservoir while flushing bypass circuit state. DE_PRIME_DRAIN_BYPASS_STATE, ///< De-prime drain dialysate from bypass circuit state. DE_PRIME_COMPLETE_STATE, ///< De-prime complete state. NUM_OF_DE_PRIME_STATES ///< Number of de-prime states. } DE_PRIME_STATE_T; // ********** private data ********** static BOOL patientDisconnectionConfirmed = FALSE; ///< Flag indicates user confirms patient disconnection. static BOOL disposableRemovalConfirmed = FALSE; ///< Flag indicates user confirms disposable removal. static HD_POST_TREATMENT_STATE_T currentPostTreatmentState; ///< Current state of post-treatment mode state machine. static DE_PRIME_STATE_T currentDePrimeState; ///< Current de-prime sub-mode state. // ********** private function prototypes ********** static HD_POST_TREATMENT_STATE_T handlePostTreatmentPatientDisconnectionState( void ); static HD_POST_TREATMENT_STATE_T handlePostTreatmentDePrimeState( void ); static HD_POST_TREATMENT_STATE_T handlePostTreatmentUnloadState( void ); static HD_POST_TREATMENT_STATE_T handlePostTreatmentVerifyState( void ); static void execDePrime( void ); static DE_PRIME_STATE_T handleDePrimeFirstDrainState( void ); static DE_PRIME_STATE_T handleDePrimeFlushBypassState( void ); static DE_PRIME_STATE_T handleDePrimeDrainBypassState( void ); /*********************************************************************//** * @brief * The initPostTreatmentMode function initializes the Post-Treatment Mode module. * @details Inputs: none * @details Outputs: Post-Treatment Mode module initialized. * @return none *************************************************************************/ void initPostTreatmentMode( void ) { patientDisconnectionConfirmed = FALSE; disposableRemovalConfirmed = FALSE; currentPostTreatmentState = HD_POST_TREATMENT_PATIENT_DISCONNECTION_STATE; currentDePrimeState = DE_PRIME_FIRST_DRAIN_STATE; } /*********************************************************************//** * @brief * The transitionToPostTreatmentMode function prepares for transition to * post-treatment mode. * @details Inputs: none * @details Outputs: none * @return none *************************************************************************/ void transitionToPostTreatmentMode( void ) { initPostTreatmentMode(); // TODO - stop any DG fill that may be in progress from an aborted treatment // Set user alarm recovery actions allowed in this mode setAlarmUserActionEnabled( ALARM_USER_ACTION_RESUME, TRUE ); setAlarmUserActionEnabled( ALARM_USER_ACTION_RINSEBACK, FALSE ); setAlarmUserActionEnabled( ALARM_USER_ACTION_END_TREATMENT, FALSE ); cmdSetDGActiveReservoir( DG_RESERVOIR_2 ); setValvePosition( VDI, VALVE_POSITION_C_CLOSE ); setValvePosition( VDO, VALVE_POSITION_C_CLOSE ); setValvePosition( VBA, VALVE_POSITION_C_CLOSE ); setValvePosition( VBV, VALVE_POSITION_C_CLOSE ); setValveAirTrap( STATE_CLOSED ); } /*********************************************************************//** * @brief * The execPostTreatmentMode function executes the Post-Treatment Mode state machine. * @details Inputs: none * @details Outputs: none * @return current state (sub-mode) *************************************************************************/ U32 execPostTreatmentMode( void ) { BOOL stop = isStopButtonPressed(); switch ( currentPostTreatmentState ) { case HD_POST_TREATMENT_PATIENT_DISCONNECTION_STATE: currentPostTreatmentState = handlePostTreatmentPatientDisconnectionState(); break; case HD_POST_TREATMENT_DE_PRIME_STATE: currentPostTreatmentState = handlePostTreatmentDePrimeState(); break; case HD_POST_TREATMENT_UNLOAD_STATE: currentPostTreatmentState = handlePostTreatmentUnloadState(); break; case HD_POST_TREATMENT_VERIFY_STATE: currentPostTreatmentState = handlePostTreatmentVerifyState(); break; default: break; } requestNewOperationMode( MODE_STAN ); // TODO - implement post treatment mode return 0; // TODO - return current state } /*********************************************************************//** * @brief * The signalAlarmActionToPostTreatmentMode function executes the given alarm action * as appropriate while in PostTreatment Mode. * @details Inputs: none * @details Outputs: given alarm action executed * @param action ID of alarm action to execute * @return none *************************************************************************/ void signalAlarmActionToPostTreatmentMode( ALARM_ACTION_T action ) { } /*********************************************************************//** * @brief * The handlePostTreatmentPatientConnectionState function waits for user * confirms patient disconnection. * @details Inputs: none * @details Outputs: processed patient disconnection confirmation * @return current state (sub-mode) *************************************************************************/ static HD_POST_TREATMENT_STATE_T handlePostTreatmentPatientDisconnectionState( void ) { HD_POST_TREATMENT_STATE_T state = HD_POST_TREATMENT_PATIENT_DISCONNECTION_STATE; if ( TRUE == patientDisconnectionConfirmed ) { setValvePosition( VDI, VALVE_POSITION_C_CLOSE ); cmdStartDGDrain( EMPTY_RESERVOIR_VOLUME_ML, FALSE ); state = HD_POST_TREATMENT_DE_PRIME_STATE; } return state; } /*********************************************************************//** * @brief * The handlePostTreatmentDePrimeState function executes de-prime operation * sub-mode state machine and transition to next state once completed. * @details Inputs: currentDePrimeState * @details Outputs: executed de-prime operation state machine. * @return current state (sub-mode) *************************************************************************/ static HD_POST_TREATMENT_STATE_T handlePostTreatmentDePrimeState( void ) { HD_POST_TREATMENT_STATE_T state = HD_POST_TREATMENT_DE_PRIME_STATE; execDePrime(); if ( DE_PRIME_COMPLETE_STATE == currentDePrimeState ) { state = HD_POST_TREATMENT_UNLOAD_STATE; } return state; } /*********************************************************************//** * @brief * The handlePostTreatmentUnloadState function waits for user confirmation * of disposable removal and doors to be closed. * @details Inputs: disposableRemovalConfirmed, doors' status * @details Outputs: transition to verify state * @return current state (sub-mode) *************************************************************************/ static HD_POST_TREATMENT_STATE_T handlePostTreatmentUnloadState( void ) { HD_POST_TREATMENT_STATE_T state = HD_POST_TREATMENT_UNLOAD_STATE; if ( ( TRUE == disposableRemovalConfirmed ) && ( STATE_CLOSED == getFPGADoorState() ) ) { state = HD_POST_TREATMENT_VERIFY_STATE; } return state; } /*********************************************************************//** * @brief * The handlePostTreatmentVerifyState function verifies cartridge removed, * syringe removed, and doors are closed before transition to standby mode. * @details Inputs: doors' status, syringe status, occlusion sensors value * @details Outputs: requested transition to standby mode * @return current state (sub-mode) *************************************************************************/ static HD_POST_TREATMENT_STATE_T handlePostTreatmentVerifyState( void ) { return HD_POST_TREATMENT_VERIFY_STATE; } /*********************************************************************//** * @brief * The execDePrime function executes the De-Prime sub-mode state machine. * @details Inputs: none * @details Outputs: none * @return current state *************************************************************************/ static void execDePrime( void ) { switch ( currentDePrimeState ) { case DE_PRIME_FIRST_DRAIN_STATE: currentDePrimeState = handleDePrimeFirstDrainState(); break; case DE_PRIME_FLUSH_BYPASS_STATE: currentDePrimeState = handleDePrimeFlushBypassState(); break; case DE_PRIME_DRAIN_BYPASS_STATE: currentDePrimeState = handleDePrimeDrainBypassState(); break; case DE_PRIME_COMPLETE_STATE: break; default: break; } } /*********************************************************************//** * @brief * The handleDePrimeFirstDrainState function sends command to DG to drain * reservoir one. * @details Inputs: none * @details Outputs: drained reservoir one * @return current state (sub-mode) *************************************************************************/ static DE_PRIME_STATE_T handleDePrimeFirstDrainState( void ) { DE_PRIME_STATE_T state = DE_PRIME_FIRST_DRAIN_STATE; if ( ( DG_MODE_CIRC == getDGOpMode() ) && ( DG_RECIRCULATE_MODE_STATE_RECIRC_WATER == getDGSubMode() ) ) { cmdSetDGActiveReservoir( DG_RESERVOIR_1 ); setValvePosition( VDI, VALVE_POSITION_C_CLOSE ); cmdStartDGDrain( EMPTY_RESERVOIR_VOLUME_ML, FALSE ); setDialInPumpTargetFlowRate( DIP_FLUSH_FLOW_RATE_ML_MIN, MOTOR_DIR_FORWARD, PUMP_CONTROL_MODE_OPEN_LOOP ); state = DE_PRIME_FLUSH_BYPASS_STATE; } return state; } /*********************************************************************//** * @brief * The handleDePrimeFlushBypassState function sends command to DG to drain * reservoir two while flushing dialysate from bypass circuit to reservoir one. * @details Inputs: none * @details Outputs: drained reservoir two, flushed dialysate from bypass circuit * @return current state (sub-mode) *************************************************************************/ static DE_PRIME_STATE_T handleDePrimeFlushBypassState( void ) { DE_PRIME_STATE_T state = DE_PRIME_FLUSH_BYPASS_STATE; if ( ( DG_MODE_CIRC == getDGOpMode() ) && ( DG_RECIRCULATE_MODE_STATE_RECIRC_WATER == getDGSubMode() ) ) { cmdSetDGActiveReservoir( DG_RESERVOIR_2 ); cmdStartDGDrain( EMPTY_RESERVOIR_VOLUME_ML, FALSE ); state = DE_PRIME_DRAIN_BYPASS_STATE; } return state; } /*********************************************************************//** * @brief * The handleDePrimeDrainBypassState function sends command to DG to drain * reservoir one, which contains flushed dialysate from bypass circuit. * @details Inputs: none * @details Outputs: drained reservoir one * @return current state (sub-mode) *************************************************************************/ static DE_PRIME_STATE_T handleDePrimeDrainBypassState( void ) { DE_PRIME_STATE_T state = DE_PRIME_DRAIN_BYPASS_STATE; if ( ( DG_MODE_CIRC == getDGOpMode() ) && ( DG_RECIRCULATE_MODE_STATE_RECIRC_WATER == getDGSubMode() ) ) { state = DE_PRIME_COMPLETE_STATE; } return state; } /**@}*/