/************************************************************************** * * Copyright (c) 2026-2026 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 StatePreTxHeparinSetup.c * * @author (last) Vijay Pamula * @date (last) 06-Jun-2026 * * @author (original) Vijay Pamula * @date (original) 06-Jun-2026 * ***************************************************************************/ #include "AlarmMgmtTD.h" #include "Messaging.h" #include "ModePreTreat.h" #include "OperationModes.h" #include "StatePreTxHeparinSetup.h" #include "SyringePump.h" #include "TxParams.h" /** * @addtogroup StatePreTxHeparinSetup * @{ */ // ********** private definitions ********** // ********** private data ********** static PRE_TX_HEPARIN_SETUP_STATE_T currentPreTxHeparinSetupState; ///< Current state of the pre-treatment heparin setup state machine. static PRE_TX_HEPARIN_SETUP_STATE_T interruptedPreTxHeparinSetupState; ///< Pre-treatment heparin setup substate interrupted by a recoverable alarm. static BOOL heparinSetupResumeRequested; ///< Flag indicates alarm requesting to resume pre-treatment heparin setup. static BOOL syringeLoadConfirmed; ///< Flag indicates user confirmed syringe load. // ********** private function prototypes ********** static void resetPreTxHeparinSetupFlags( void ); ///< Reset all pre-treatment heparin setup signal flags. static void setupPreTxHeparinPreload( void ); ///< Configure actuators for pre-treatment heparin preload state. static void setupPreTxHeparinAwaitSyringeLoadConfirmation( void ); ///< Configure actuators for awaiting syringe load confirmation state. static void setupPreTxHeparinSeek( void ); ///< Configure actuators for pre-treatment heparin seek state. static void setupPreTxHeparinPrime( void ); ///< Configure actuators for pre-treatment heparin prime state. static void setupPreTxHeparinOcclusionCheck( void ); ///< Configure actuators for pre-treatment heparin occlusion check state. static void setupPreTxHeparinBolus( void ); ///< Configure actuators for pre-treatment heparin bolus state. static void setupPreTxHeparinPaused( void ); ///< Configure actuators for pre-treatment heparin paused state. static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinPreloadState( void ); ///< Handle pre-treatment heparin preload state. static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinAwaitSyringeLoadConfirmationState( void ); ///< Handle awaiting syringe load confirmation state. static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinSeekState( void ); ///< Handle pre-treatment heparin seek state. static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinPrimeState( void ); ///< Handle pre-treatment heparin prime state. static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinOcclusionCheckState( void ); ///< Handle pre-treatment heparin occlusion check state. static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinBolusState( void ); ///< Handle pre-treatment heparin bolus state. static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinPausedState( void ); ///< Handle pre-treatment heparin paused state. /*********************************************************************//** * @brief * The initPreTxHeparinSetup function initializes the pre-treatment * heparin setup state machine. * @details Inputs: none * @details Outputs: Pre-treatment heparin setup initialized. * @return none *************************************************************************/ void initPreTxHeparinSetup( void ) { currentPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_PRELOAD_STATE; interruptedPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_PRELOAD_STATE; resetPreTxHeparinSetupFlags(); } /*********************************************************************//** * @brief * The transitionToPreTxHeparinSetup function prepares for transition * into the pre-treatment heparin setup state. * @details Inputs: none * @details Outputs: Heparin setup initialized. * @return none *************************************************************************/ void transitionToPreTxHeparinSetup( void ) { initPreTxHeparinSetup(); setupPreTxHeparinPreload(); setCurrentSubState( (U32)currentPreTxHeparinSetupState ); } /*********************************************************************//** * @brief * The execPreTxHeparinSetup function executes the pre-treatment heparin * setup state machine. * @details Inputs: currentPreTxHeparinSetupState * @details Outputs: currentPreTxHeparinSetupState * @return none *************************************************************************/ void execPreTxHeparinSetup( void ) { PRE_TX_HEPARIN_SETUP_STATE_T priorSubState = currentPreTxHeparinSetupState; switch ( currentPreTxHeparinSetupState ) { case PRE_TX_HEPARIN_SETUP_PRELOAD_STATE: currentPreTxHeparinSetupState = handlePreTxHeparinPreloadState(); break; case PRE_TX_HEPARIN_SETUP_AWAIT_SYRINGE_LOAD_CONFIRMATION_STATE: currentPreTxHeparinSetupState = handlePreTxHeparinAwaitSyringeLoadConfirmationState(); break; case PRE_TX_HEPARIN_SETUP_SEEK_STATE: currentPreTxHeparinSetupState = handlePreTxHeparinSeekState(); break; case PRE_TX_HEPARIN_SETUP_PRIME_STATE: currentPreTxHeparinSetupState = handlePreTxHeparinPrimeState(); break; case PRE_TX_HEPARIN_SETUP_OCCLUSION_CHECK_STATE: currentPreTxHeparinSetupState = handlePreTxHeparinOcclusionCheckState(); break; case PRE_TX_HEPARIN_SETUP_BOLUS_STATE: currentPreTxHeparinSetupState = handlePreTxHeparinBolusState(); break; case PRE_TX_HEPARIN_SETUP_PAUSED_STATE: currentPreTxHeparinSetupState = handlePreTxHeparinPausedState(); break; default: SET_ALARM_WITH_2_U32_DATA( ALARM_ID_TD_SOFTWARE_FAULT, SW_FAULT_ID_TD_INVALID_PRE_TX_HEPARIN_SETUP_STATE, currentPreTxHeparinSetupState ); break; } if ( priorSubState != currentPreTxHeparinSetupState ) { setCurrentSubState( (U32)currentPreTxHeparinSetupState ); SEND_EVENT_WITH_2_U32_DATA( TD_EVENT_SUB_STATE_CHANGE, priorSubState, currentPreTxHeparinSetupState ); } resetPreTxHeparinSetupFlags(); } /*********************************************************************//** * @brief * The getPreTxHeparinSetupState function returns the current state of the * pre-treatment heparin setup state machine. * @details Inputs: currentPreTxHeparinSetupState * @details Outputs: none * @return Current pre-treatment heparin setup state. *************************************************************************/ U32 getPreTxHeparinSetupState( void ) { return (U32)currentPreTxHeparinSetupState; } /*********************************************************************//** * @brief * The signalResumePreTxHeparinSetup function signals a resume request for * the pre-treatment heparin setup state machine. * @details Inputs: none * @details Outputs: heparinSetupResumeRequested * @return none *************************************************************************/ void signalResumePreTxHeparinSetup( void ) { heparinSetupResumeRequested = TRUE; } /*********************************************************************//** * @brief * The signalPreTxHeparinSyringeLoadConfirmed function signals that the * user confirmed syringe load. * @details Inputs: none * @details Outputs: syringeLoadConfirmed * @return none *************************************************************************/ void signalPreTxHeparinSyringeLoadConfirmed( void ) { syringeLoadConfirmed = TRUE; } /*********************************************************************//** * @brief * The resetPreTxHeparinSetupFlags function resets all signal flags used by * the pre-treatment heparin setup state machine. * @details Inputs: none * @details Outputs: Signal flags reset. * @return none *************************************************************************/ static void resetPreTxHeparinSetupFlags( void ) { heparinSetupResumeRequested = FALSE; syringeLoadConfirmed = FALSE; } /*********************************************************************//** * @brief * The setupPreTxHeparinPreload function configures the syringe pump for * pre-treatment heparin preload. * @details Inputs: none * @details Outputs: Syringe pump preload requested. * @return none *************************************************************************/ static void setupPreTxHeparinPreload( void ) { stopSyringePump(); resetPreLoadStatus(); (void)preloadSyringePlunger(); } /*********************************************************************//** * @brief * The setupPreTxHeparinAwaitSyringeLoadConfirmation function configures * the syringe pump while waiting for syringe load confirmation. * @details Inputs: none * @details Outputs: Syringe pump stopped. * @return none *************************************************************************/ static void setupPreTxHeparinAwaitSyringeLoadConfirmation( void ) { stopSyringePump(); } /*********************************************************************//** * @brief * The setupPreTxHeparinSeek function configures the syringe pump for seek. * @details Inputs: none * @details Outputs: Syringe pump seek requested. * @return none *************************************************************************/ static void setupPreTxHeparinSeek( void ) { stopSyringePump(); (void)seekSyringePlunger(); } /*********************************************************************//** * @brief * The setupPreTxHeparinPrime function configures the syringe pump for * heparin line prime. * @details Inputs: none * @details Outputs: Syringe pump prime requested. * @return none *************************************************************************/ static void setupPreTxHeparinPrime( void ) { stopSyringePump(); (void)primeSyringePump(); } /*********************************************************************//** * @brief * The setupPreTxHeparinOcclusionCheck function configures the syringe pump * for the occlusion check state. * @details Inputs: none * @details Outputs: Syringe pump stopped. * @return none *************************************************************************/ static void setupPreTxHeparinOcclusionCheck( void ) { stopSyringePump(); } /*********************************************************************//** * @brief * The setupPreTxHeparinBolus function configures the syringe pump for * heparin bolus delivery. * @details Inputs: none * @details Outputs: Syringe pump bolus requested. * @return none *************************************************************************/ static void setupPreTxHeparinBolus( void ) { stopSyringePump(); (void)startHeparinBolus(); } /*********************************************************************//** * @brief * The setupPreTxHeparinPaused function configures the syringe pump for the * paused state. * @details Inputs: none * @details Outputs: Syringe pump stopped. * @return none *************************************************************************/ static void setupPreTxHeparinPaused( void ) { stopSyringePump(); } /*********************************************************************//** * @brief * The handlePreTxHeparinPreloadState function handles the preload state. * @details \b Inputs: none * @details \b Outputs: Next pre-treatment heparin setup state. * @return Current or next pre-treatment heparin setup state. *************************************************************************/ static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinPreloadState( void ) { PRE_TX_HEPARIN_SETUP_STATE_T state = PRE_TX_HEPARIN_SETUP_PRELOAD_STATE; if ( TRUE == doesAlarmStatusIndicateStop() ) { interruptedPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_PRELOAD_STATE; setupPreTxHeparinPaused(); state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; } else if ( ( FALSE == isSyringePumpRunning() ) && ( FALSE == isSyringePumpPreLoaded() ) ) { setupPreTxHeparinPreload(); } else if ( TRUE == isSyringePumpPreLoaded() ) { setupPreTxHeparinAwaitSyringeLoadConfirmation(); state = PRE_TX_HEPARIN_SETUP_AWAIT_SYRINGE_LOAD_CONFIRMATION_STATE; } return state; } /*********************************************************************//** * @brief * The handlePreTxHeparinAwaitSyringeLoadConfirmationState function handles * the await syringe load confirmation state. * @details \b Inputs: none * @details \b Outputs: Next pre-treatment heparin setup state. * @return Current or next pre-treatment heparin setup state. *************************************************************************/ static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinAwaitSyringeLoadConfirmationState( void ) { PRE_TX_HEPARIN_SETUP_STATE_T state = PRE_TX_HEPARIN_SETUP_AWAIT_SYRINGE_LOAD_CONFIRMATION_STATE; if ( TRUE == doesAlarmStatusIndicateStop() ) { interruptedPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_AWAIT_SYRINGE_LOAD_CONFIRMATION_STATE; setupPreTxHeparinPaused(); state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; } else if ( TRUE == syringeLoadConfirmed ) { setupPreTxHeparinSeek(); state = PRE_TX_HEPARIN_SETUP_SEEK_STATE; } return state; } /*********************************************************************//** * @brief * The handlePreTxHeparinSeekState function handles the seek state. * @details \b Alarms: ALARM_ID_TD_SYRINGE_PUMP_NOT_ENOUGH_HEPARIN_ALARM * if the syringe contains insufficient heparin for the prescribed treatment. * @details \b Inputs: none * @details \b Outputs: Next pre-treatment heparin setup state. * @return Current or next pre-treatment heparin setup state. *************************************************************************/ static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinSeekState( void ) { PRE_TX_HEPARIN_SETUP_STATE_T state = PRE_TX_HEPARIN_SETUP_SEEK_STATE; if ( TRUE == doesAlarmStatusIndicateStop() ) { interruptedPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_SEEK_STATE; setupPreTxHeparinPaused(); state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; } else if ( TRUE == isSyringePlungerFound() ) { if ( TRUE == isSyringeVolumeAdequate() ) { setupPreTxHeparinPrime(); state = PRE_TX_HEPARIN_SETUP_PRIME_STATE; } else { // Syringe plunger was found, but available heparin volume is not enough for treatment. activateAlarmNoData( ALARM_ID_TD_SYRINGE_PUMP_NOT_ENOUGH_HEPARIN_ALARM ); interruptedPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_SEEK_STATE; setupPreTxHeparinPaused(); state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; } } return state; } /*********************************************************************//** * @brief * The handlePreTxHeparinPrimeState function handles the prime state. * @details \b Inputs: none * @details \b Outputs: Next pre-treatment heparin setup state. * @return Current or next pre-treatment heparin setup state. *************************************************************************/ static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinPrimeState( void ) { PRE_TX_HEPARIN_SETUP_STATE_T state = PRE_TX_HEPARIN_SETUP_PRIME_STATE; if ( TRUE == doesAlarmStatusIndicateStop() ) { interruptedPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_PRIME_STATE; setupPreTxHeparinPaused(); state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; } else if ( TRUE == isSyringePumpPrimed() ) { setupPreTxHeparinOcclusionCheck(); state = PRE_TX_HEPARIN_SETUP_OCCLUSION_CHECK_STATE; } return state; } /*********************************************************************//** * @brief * The handlePreTxHeparinOcclusionCheckState function handles the heparin * pump occlusion check state. * @details \b Alarms: ALARM_ID_TD_SYRINGE_PUMP_OCCLUSION if the * heparin pump occlusion check fails. * @details \b Inputs: none * @details \b Outputs: Next pre-treatment heparin setup state. * @return Current or next pre-treatment heparin setup state. *************************************************************************/ static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinOcclusionCheckState( void ) { PRE_TX_HEPARIN_SETUP_STATE_T state = PRE_TX_HEPARIN_SETUP_OCCLUSION_CHECK_STATE; if ( TRUE == doesAlarmStatusIndicateStop() ) { interruptedPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_OCCLUSION_CHECK_STATE; setupPreTxHeparinPaused(); state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; } else if ( FALSE == checkForSyringeOcclusion( FALSE ) ) { // Occlusion check passed. Continue to bolus if prescribed; otherwise continue to Patient Connection. if ( getTreatmentParameterF32( TREATMENT_PARAM_HEPARIN_BOLUS_VOLUME ) > 0.0F ) { setupPreTxHeparinBolus(); state = PRE_TX_HEPARIN_SETUP_BOLUS_STATE; } else { PreTxRequestContinueFromHeparinSetupRequested(); } } else { // Occlusion check failed. Alarm is handled by checkForSyringeOcclusion(). interruptedPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_OCCLUSION_CHECK_STATE; setupPreTxHeparinPaused(); state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; } return state; } /*********************************************************************//** * @brief * The handlePreTxHeparinBolusState function handles the bolus state. * @details \b Inputs: none * @details \b Outputs: Next pre-treatment heparin setup state. * @return Current or next pre-treatment heparin setup state. *************************************************************************/ static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinBolusState( void ) { PRE_TX_HEPARIN_SETUP_STATE_T state = PRE_TX_HEPARIN_SETUP_BOLUS_STATE; if ( TRUE == doesAlarmStatusIndicateStop() ) { interruptedPreTxHeparinSetupState = PRE_TX_HEPARIN_SETUP_BOLUS_STATE; setupPreTxHeparinPaused(); state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; } else if ( TRUE == isSyringePumpStopped() ) { PreTxRequestContinueFromHeparinSetupRequested(); } return state; } /*********************************************************************//** * @brief * The handlePreTxHeparinPausedState function handles the paused state. * @details \b Inputs: none * @details \b Outputs: Next pre-treatment heparin setup state. * @return Current or next pre-treatment heparin setup state. *************************************************************************/ static PRE_TX_HEPARIN_SETUP_STATE_T handlePreTxHeparinPausedState( void ) { PRE_TX_HEPARIN_SETUP_STATE_T state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; if ( TRUE == heparinSetupResumeRequested ) { if ( ( PRE_TX_HEPARIN_SETUP_PRELOAD_STATE == interruptedPreTxHeparinSetupState ) || ( PRE_TX_HEPARIN_SETUP_AWAIT_SYRINGE_LOAD_CONFIRMATION_STATE == interruptedPreTxHeparinSetupState ) || ( PRE_TX_HEPARIN_SETUP_SEEK_STATE == interruptedPreTxHeparinSetupState ) ) { retractSyringePump(); state = PRE_TX_HEPARIN_SETUP_PRELOAD_STATE; } else { state = interruptedPreTxHeparinSetupState; switch ( state ) { case PRE_TX_HEPARIN_SETUP_PRIME_STATE: setupPreTxHeparinPrime(); break; case PRE_TX_HEPARIN_SETUP_OCCLUSION_CHECK_STATE: setupPreTxHeparinOcclusionCheck(); break; case PRE_TX_HEPARIN_SETUP_BOLUS_STATE: setupPreTxHeparinBolus(); break; default: SET_ALARM_WITH_2_U32_DATA( ALARM_ID_TD_SOFTWARE_FAULT, SW_FAULT_ID_TD_INVALID_PRE_TX_HEPARIN_SETUP_STATE, interruptedPreTxHeparinSetupState ); state = PRE_TX_HEPARIN_SETUP_PAUSED_STATE; break; } } } return state; } /**@}*/