Index: firmware/App/Modes/ModeTreatment.c =================================================================== diff -u -rfa356a2bce909141f45c6832659fa1ceea5bfbba -r49dba1e95bb3763b4c150e7a80b84a65264a7ca8 --- firmware/App/Modes/ModeTreatment.c (.../ModeTreatment.c) (revision fa356a2bce909141f45c6832659fa1ceea5bfbba) +++ firmware/App/Modes/ModeTreatment.c (.../ModeTreatment.c) (revision 49dba1e95bb3763b4c150e7a80b84a65264a7ca8) @@ -78,10 +78,11 @@ static U32 lastTreatmentTimeStamp; ///< Last time elapsed treatment time was recorded (a timestamp in ms). static U32 treatmentTimeBroadcastTimerCtr; ///< Treatment data broadcast timer counter used to schedule when to transmit data. static U32 treatmentParamsRangesBroadcastTimerCtr; ///< Treatment parameter ranges broadcast timer counter used to schedule when to transmit updated ranges. -// TODO - test code - remove later -static BUTTON_STATE_T lastOffButtonState = BUTTON_STATE_RELEASED; -static BOOL pendingUserEndTreatmentRequest; ///< Flag indicates user has requested treatment end. +static BOOL alarmStopSignalled; ///< Flag indicates an alarm w/ stop property was triggered. +static BOOL resumeTreatmentAlarmResponseRequest; ///< Flag indicates user has requested treatment resume. +static BOOL initiateRinsebackAlarmResponseRequest; ///< Flag indicates user has requested rinseback. +static BOOL endTreatmentAlarmResponseRequest; ///< Flag indicates user has requested treatment end. static U32 pendingParamChangesTimer; ///< User required to confirm UF volume change within 1 minute. static F32 pendingUFVolumeChange; ///< An ultrafiltration volume change (mL) is pending user confirmation. @@ -90,10 +91,14 @@ // ********** private function prototypes ********** +static void resetAlarmResponseFlags( void ); static void broadcastTreatmentSettingsRanges( void ); static TREATMENT_STATE_T handleTreatmentStartState( void ); +static TREATMENT_STATE_T handleTreatmentBloodPrimeState( void ); static TREATMENT_STATE_T handleTreatmentDialysisState( void ); static TREATMENT_STATE_T handleTreatmentStopState( void ); +static TREATMENT_STATE_T handleTreatmentRinsebackState( void ); +static TREATMENT_STATE_T handleTreatmentRecircState( void ); /*********************************************************************//** * @brief @@ -120,7 +125,7 @@ presMaxUFVolumeML = 0.0; presUFRate = 0.0; - pendingUserEndTreatmentRequest = FALSE; + resetAlarmResponseFlags(); pendingParamChangesTimer = 0; pendingUFVolumeChange = 0.0; @@ -130,6 +135,21 @@ /*********************************************************************//** * @brief + * The resetAlarmResponseFlags function resets the alarm response flags. + * @details Inputs: none + * @details Outputs: flags set to FALSE + * @return none + *************************************************************************/ +static void resetAlarmResponseFlags( void ) +{ + alarmStopSignalled = FALSE; + resumeTreatmentAlarmResponseRequest = FALSE; + initiateRinsebackAlarmResponseRequest = FALSE; + endTreatmentAlarmResponseRequest = FALSE; +} + +/*********************************************************************//** + * @brief * The transitionToTreatmentMode function prepares for transition to treatment mode. * @details Inputs: none * @details Outputs: @@ -197,7 +217,7 @@ * @details Outputs: none * @return bloodIsPrimed *************************************************************************/ -BOOL getBloodIsPrimed( void ) // Determine whether the blood-side circuit of the dialyzer has been primed with blood +BOOL getBloodIsPrimed( void ) { return bloodIsPrimed; } @@ -232,72 +252,19 @@ switch( action ) { case ALARM_ACTION_STOP: - switch ( currentTreatmentState ) - { - case TREATMENT_START_STATE: - case TREATMENT_DIALYSIS_STATE: - stopDialysis(); - transitionToTreatmentStop(); - currentTreatmentState = TREATMENT_STOP_STATE; - break; - - case TREATMENT_RINSEBACK_STATE: - signalStopRinseback(); - break; - - case TREATMENT_RECIRC_STATE: - signalStopTreatmentRecirc(); - break; - - default: - // Ignore - break; - } + alarmStopSignalled = TRUE; break; case ALARM_ACTION_RESUME: - switch ( currentTreatmentState ) - { - case TREATMENT_STOP_STATE: - lastTreatmentTimeStamp = getMSTimerCount(); - startDialysis(); - transitionToDialysis(); - currentTreatmentState = TREATMENT_DIALYSIS_STATE; - break; - - default: - // Ignore - break; - } + resumeTreatmentAlarmResponseRequest = TRUE; break; case ALARM_ACTION_RINSEBACK: - switch ( currentTreatmentState ) - { - case TREATMENT_STOP_STATE: - lastTreatmentTimeStamp = getMSTimerCount(); - startDialysis(); - transitionToDialysis(); - currentTreatmentState = TREATMENT_DIALYSIS_STATE; - break; - - default: - // Ignore - break; - } + initiateRinsebackAlarmResponseRequest = TRUE; break; case ALARM_ACTION_END_TREATMENT: - switch ( currentTreatmentState ) - { - case TREATMENT_STOP_STATE: - pendingUserEndTreatmentRequest = TRUE; - break; - - default: - // Ignore - break; - } + endTreatmentAlarmResponseRequest = TRUE; break; case ALARM_ACTION_ACK: @@ -333,6 +300,10 @@ currentTreatmentState = handleTreatmentStartState(); break; + case TREATMENT_BLOOD_PRIME_STATE: + currentTreatmentState = handleTreatmentBloodPrimeState(); + break; + case TREATMENT_DIALYSIS_STATE: currentTreatmentState = handleTreatmentDialysisState(); break; @@ -342,11 +313,11 @@ break; case TREATMENT_RINSEBACK_STATE: - // TODO - implement + currentTreatmentState = handleTreatmentRinsebackState(); break; case TREATMENT_RECIRC_STATE: - // TODO - implement + currentTreatmentState = handleTreatmentRecircState(); break; case TREATMENT_DIALYSIS_END_STATE: @@ -364,6 +335,10 @@ currentTreatmentState = TREATMENT_END_STATE; break; } + + // Alarm response request flags should be handled at this point, reset in case not handled in current state + resetAlarmResponseFlags(); + // Broadcast treatment data broadcastTreatmentTimeAndState(); broadcastTreatmentSettingsRanges(); @@ -378,22 +353,20 @@ /*********************************************************************//** * @brief * The handleTreatmentStartState function handles the Start state of - * the Treatment Mode state machine. + * the Treatment Mode state machine. Should only pass through this state + * once at very beginning of treatment. * @details Inputs: none * @details Outputs: treatmentTimeMS, lastTreatmentTimeStamp * @return next treatment mode state *************************************************************************/ -static TREATMENT_STATE_T handleTreatmentStartState( void ) // TODO - we need a blood prime state between start and dialysis sub-modes +static TREATMENT_STATE_T handleTreatmentStartState( void ) { - TREATMENT_STATE_T result = TREATMENT_DIALYSIS_STATE; + TREATMENT_STATE_T result = TREATMENT_BLOOD_PRIME_STATE; // Initialize treatment time treatmentTimeMS = 0; lastTreatmentTimeStamp = getMSTimerCount(); - setRinsebackIsCompleted( FALSE ); - //setBloodIsPrimed( TRUE ); TODO - call when blood prime is completed - presTreatmentTimeSecs = SEC_PER_MIN * getTreatmentParameterU32( TREATMENT_PARAM_TREATMENT_DURATION ); presBloodFlowRate = getTreatmentParameterU32( TREATMENT_PARAM_BLOOD_FLOW ); presDialysateFlowRate = getTreatmentParameterU32( TREATMENT_PARAM_DIALYSATE_FLOW ); @@ -409,6 +382,43 @@ /*********************************************************************//** * @brief + * The handleTreatmentBloodPrimeState function handles the blood prime state of + * the Treatment Mode state machine. + * @details Inputs: none + * @details Outputs: none + * @return next treatment mode state + *************************************************************************/ +static TREATMENT_STATE_T handleTreatmentBloodPrimeState( void ) // TODO - need separate module w/ states for this sub-mode (signal functions in treatment mode to be called if sub-mode chaning) +{ + TREATMENT_STATE_T result = TREATMENT_BLOOD_PRIME_STATE; + + setRinsebackIsCompleted( FALSE ); + + if ( TRUE == alarmStopSignalled ) + { + alarmStopSignalled = FALSE; + // TODO - stopBloodPrime(); + transitionToTreatmentStop(); + result = TREATMENT_STOP_STATE; + } + else + { + if ( TRUE ) // TODO - when blood prime done signal + { + setBloodIsPrimed( TRUE ); // TODO - call when blood prime is completed + result = TREATMENT_DIALYSIS_STATE; + } + else + { + //execTreatmentBloodPrime(); // TODO - implement this state + } + } + + return result; +} + +/*********************************************************************//** + * @brief * The handleTreatmentDialysisState function handles the Dialysis state of * the Treatment Mode state machine. * @details Inputs: none @@ -422,39 +432,33 @@ U32 newTime = getMSTimerCount(); U32 msSinceLast = calcTimeBetween( lastTreatmentTimeStamp, newTime ); - // Update treatment time (unless delivering a saline bolus) - if ( getDialysisState() != DIALYSIS_SALINE_BOLUS_STATE ) + if ( TRUE == alarmStopSignalled ) { - treatmentTimeMS += msSinceLast; + alarmStopSignalled = FALSE; + stopDialysis(); + transitionToTreatmentStop(); + result = TREATMENT_STOP_STATE; } - lastTreatmentTimeStamp = newTime; - - // End treatment if treatment duration has been reached - if ( CALC_ELAPSED_TREAT_TIME_IN_SECS() >= presTreatmentTimeSecs ) - { - result = TREATMENT_END_STATE; - } - // Otherwise, execute state machine for treatment dialysis sub-mode else { - execDialysis(); - } + // Update treatment time (unless delivering a saline bolus) + if ( getDialysisState() != DIALYSIS_SALINE_BOLUS_STATE ) + { + treatmentTimeMS += msSinceLast; + } + lastTreatmentTimeStamp = newTime; - // TODO - test code - remove later - if ( getOffButtonState() == BUTTON_STATE_PRESSED ) - { - if ( lastOffButtonState == BUTTON_STATE_RELEASED ) + // End treatment if treatment duration has been reached + if ( CALC_ELAPSED_TREAT_TIME_IN_SECS() >= presTreatmentTimeSecs ) { - lastOffButtonState = BUTTON_STATE_PRESSED; - stopDialysis(); - transitionToTreatmentStop(); - result = TREATMENT_STOP_STATE; + result = TREATMENT_END_STATE; } + // Otherwise, execute state machine for treatment dialysis sub-mode + else + { + execDialysis(); + } } - else - { - lastOffButtonState = BUTTON_STATE_RELEASED; - } return result; } @@ -471,34 +475,89 @@ { TREATMENT_STATE_T result = TREATMENT_STOP_STATE; + // If user requests resumption of treatment, resume treatment + if ( TRUE == resumeTreatmentAlarmResponseRequest ) + { + resumeTreatmentAlarmResponseRequest = FALSE; + if ( TRUE == getBloodIsPrimed() ) + { + lastTreatmentTimeStamp = getMSTimerCount(); + startDialysis(); + transitionToDialysis(); + result = TREATMENT_DIALYSIS_STATE; + } + else + { + // TODO - transitionToBloodPrime(); + result = TREATMENT_BLOOD_PRIME_STATE; + } + } + // If user requests rinseback, go to rinseback + else if ( TRUE == initiateRinsebackAlarmResponseRequest ) + { + initiateRinsebackAlarmResponseRequest = FALSE; + transitionToRinseback(); + result = TREATMENT_RINSEBACK_STATE; + } // If user requests treatment end, end treatment - if ( TRUE == pendingUserEndTreatmentRequest ) + else if ( TRUE == endTreatmentAlarmResponseRequest ) { + endTreatmentAlarmResponseRequest = FALSE; + // TODO - transition to end state result = TREATMENT_END_STATE; } + // Otherwise execute state machine for treatment stop sub-mode else { - // Execute state machine for treatment stop sub-mode execTreatmentStop(); } - // TODO - test code - remove later - if ( getOffButtonState() == BUTTON_STATE_PRESSED ) + return result; +} + +/*********************************************************************//** + * @brief + * The handleTreatmentRinsebackState function executes the rinseback state of the + * Treatment Mode state machine. + * @details Inputs: none + * @details Outputs: treatment rinseback sub-mode executed. + * @return next treatment mode state + *************************************************************************/ +static TREATMENT_STATE_T handleTreatmentRinsebackState( void ) +{ + TREATMENT_STATE_T result = TREATMENT_RINSEBACK_STATE; + + if ( TRUE == alarmStopSignalled ) { - if ( lastOffButtonState == BUTTON_STATE_RELEASED ) - { - lastOffButtonState = BUTTON_STATE_PRESSED; - lastTreatmentTimeStamp = getMSTimerCount(); - startDialysis(); - transitionToDialysis(); - result = TREATMENT_DIALYSIS_STATE; - } + alarmStopSignalled = FALSE; + signalStopRinseback(); } - else + + execRinseback(); + + return result; +} + +/*********************************************************************//** + * @brief + * The handleTreatmentRecircState function executes the re-circulate state of the + * Treatment Mode state machine. + * @details Inputs: none + * @details Outputs: treatment re-circulate sub-mode executed. + * @return next treatment mode state + *************************************************************************/ +static TREATMENT_STATE_T handleTreatmentRecircState( void ) +{ + TREATMENT_STATE_T result = TREATMENT_RINSEBACK_STATE; + + if ( TRUE == alarmStopSignalled ) { - lastOffButtonState = BUTTON_STATE_RELEASED; + alarmStopSignalled = FALSE; + signalStopTreatmentRecirc(); } + execTreatmentRecirc(); + return result; }