Index: firmware/App/Modes/ModePreTreat.c =================================================================== diff -u -r85c561f68280f7390dc9e8b7013cbcb85d50f424 -r36eda8f2799310ff842cf035a3eaa96c7c2bccdb --- firmware/App/Modes/ModePreTreat.c (.../ModePreTreat.c) (revision 85c561f68280f7390dc9e8b7013cbcb85d50f424) +++ firmware/App/Modes/ModePreTreat.c (.../ModePreTreat.c) (revision 36eda8f2799310ff842cf035a3eaa96c7c2bccdb) @@ -7,8 +7,8 @@ * * @file ModePreTreat.c * -* @author (last) Sean Nash -* @date (last) 20-Apr-2023 +* @author (last) Dara Navaei +* @date (last) 04-May-2023 * * @author (original) Dara Navaei * @date (original) 05-Nov-2019 @@ -48,14 +48,17 @@ #define PRE_TREATMENT_FLUSH_FILL_TARGET_TEMP_C 45.0F ///< Pre treatment flush fill target temperature in C. #define PRE_TREATMENT_NORMAL_FILL_TARGET_TEMP_C ( 37.0F + 2.0F ) ///< Pre treatment normal fill target temperature in C. -#define PRE_TREATMENT_MIN_FILL_RESERVOIR_VOLUME_ML 500 ///< Fill reservoir to this volume minimum to prep volume during development. -#define PRE_TREATMENT_FLUSH_RESERVOIR_VOLUME_ML 500 ///< Fill reservoir to this volume (in mL) to flush filter and lines. -#define PRE_TREATMENT_FILL_RESERVOIR_ONE_VOLUME_ML 1300 ///< Fill reservoir one to this volume (in mL) during pre-treatment mode. -#define PRE_TREATMENT_FILL_RESERVOIR_TWO_VOLUME_ML 600 ///< Fill reservoir two to this volume (in mL) during pre-treatment mode. -#define PRE_TREATMENT_FULL_RESERVOIR_VOLUME_ML 1500 ///< Fill reservoir to this volume minimum to prep volume during development. +#define PRE_TREATMENT_MIN_FILL_RESERVOIR_VOLUME_ML 500 ///< Fill reservoir to this volume minimum to prep volume during development. +#define PRE_TREATMENT_FLUSH_RESERVOIR_VOLUME_ML 500 ///< Fill reservoir to this volume (in mL) to flush filter and lines. +#define PRE_TREATMENT_FILL_RESERVOIR_ONE_VOLUME_ML 1300 ///< Fill reservoir one to this volume (in mL) during pre-treatment mode. +#define PRE_TREATMENT_FILL_RESERVOIR_TWO_VOLUME_ML 600 ///< Fill reservoir two to this volume (in mL) during pre-treatment mode. +#define PRE_TREATMENT_FULL_RESERVOIR_VOLUME_ML 1500 ///< Fill reservoir to this volume minimum to prep volume during development. #define PRE_TREATMENT_FLUSH_COUNT 2 ///< Number of flush cycles for each reservoir. +#define PRE_TREATMENT_TEST_CONFIG_MIN_RSRVR_VOL_ML 1400 ///< Pre-treatment test configuration minimum reservoir volume in milliliters. +#define PRE_TREATMENT_TEST_CONFIG_MAX_RSRVR_VOL_ML 1575 ///< Pre-treatment test configuration maximum reservoir volume in milliliters. + typedef struct { BOOL initialDrain; ///< Flags indicate whether a reservoir has been requested to initially drain. @@ -140,6 +143,9 @@ static U32 getPreTreatmentFillVolume( DG_RESERVOIR_ID_T inactiveRes ); static void setPreTreatmentHeatingParams( F32 targetTempC, U32 targetVolML, F32 targetFillFlowLPM, U32 dialysateFlowMLPM ); +// Test configuration teset function +static void execPreTreatmentTestConfigReservoirMgmt( void ); + /*********************************************************************//** * @brief * The initPreTreatmentMode function initializes the Pre-Treatment Mode module. @@ -236,8 +242,17 @@ doorClosedRequired( FALSE, FALSE ); - // Start pre-treatment mode in sample water state - transitionToSampleWater(); + if ( getTestConfigStatus( TEST_CONFIG_EXPEDITE_PRE_TREATMENT ) != TRUE ) + { + // Start pre-treatment mode in sample water state + transitionToSampleWater(); + } + else + { + cmdStartDG(); + transitionToPatientConnection(); + currentPreTreatmentState = HD_PRE_TREATMENT_PATIENT_CONNECTION_STATE; + } return currentPreTreatmentState; } @@ -298,8 +313,16 @@ break; } - // Execute reservoir management for pre-treatment mode - execPreTreatmentReservoirMgmt(); + if ( getTestConfigStatus( TEST_CONFIG_EXPEDITE_PRE_TREATMENT ) != TRUE ) + { + // Execute reservoir management for pre-treatment mode + execPreTreatmentReservoirMgmt(); + } + else + { + // If the expedite pre-treatment test configuration is set, the reservoir management is executed differently + execPreTreatmentTestConfigReservoirMgmt(); + } // Alarm response request flags should be handled at this point, reset in case not handled in current state resetSignalFlags(); @@ -757,12 +780,8 @@ fillReservoirOneStartRequested = TRUE; transitionToNoCartSelfTests(); } -#ifndef _RELEASE_ - if ( SW_CONFIG_DISABLE_VALUE == getSoftwareConfigStatus( SW_CONFIG_DISABLE_AIR_PUMP ) ) // Allow reservoir flushes now if air pump not disabled -#endif - { - signalAllowDGFlushFills(); - } + + signalAllowDGFlushFills(); } return state; @@ -1087,18 +1106,25 @@ * @brief * The handlePatientConnectionWait4TreatmentStartState function handles the wait * for treatment start state of pre-treatment patient connection sub-mode. - * @details Inputs: treatmentStartRequested + * @details Inputs: treatmentStartRequested, currentReservoirMgmtState * @details Outputs: none * @return next patient connection state *************************************************************************/ static HD_PRE_TREATMENT_PAT_CONN_STATE_T handlePatientConnectionWait4TreatmentStartState( void ) { HD_PRE_TREATMENT_PAT_CONN_STATE_T nextState = PRE_TREATMENT_PAT_CONN_WAIT_FOR_TREATMENT_START_STATE; + BOOL startTreatment = TRUE; - if ( TRUE == treatmentStartRequested ) + if ( ( TRUE == getTestConfigStatus( TEST_CONFIG_EXPEDITE_PRE_TREATMENT ) ) && + ( currentReservoirMgmtState != PRE_TREATMENT_RESERVOIR_MGMT_COMPLETE_STATE ) ) { - DG_RESERVOIR_ID_T const activeRes = getDGActiveReservoir(); + startTreatment = FALSE; + } + if ( ( TRUE == treatmentStartRequested ) && ( TRUE == startTreatment ) ) + { + DG_RESERVOIR_ID_T activeRes = getDGActiveReservoir(); + setStartReservoirVolume( activeRes ); requestNewOperationMode( MODE_TREA ); } @@ -1212,8 +1238,8 @@ { if ( ( DG_MODE_GENE == dgOpMode ) && ( DG_GEN_IDLE_MODE_STATE_FLUSH_WATER == dgSubMode ) ) { - state = PRE_TREATMENT_RESERVOIR_MGMT_DRAIN_CMD_RESP_STATE; - cmdStartDGDrain( DRAIN_RESERVOIR_TO_VOLUME_ML, TRUE, FALSE, TRUE ); + state = PRE_TREATMENT_RESERVOIR_MGMT_DRAIN_CMD_RESP_STATE; + cmdStartDGDrain( DRAIN_RESERVOIR_TO_VOLUME_ML, TRUE, FALSE, TRUE ); } } @@ -1469,6 +1495,11 @@ if ( ( TRUE == reservoirStatus[ DG_RESERVOIR_1 ].fillComplete ) && ( TRUE == reservoirStatus[ DG_RESERVOIR_2 ].fillComplete ) ) { + F32 targetTempC = getTreatmentParameterF32( TREATMENT_PARAM_DIALYSATE_TEMPERATURE ); + U32 dialysateFlowMLPM = getTreatmentParameterU32( TREATMENT_PARAM_DIALYSATE_FLOW ); + + // Set the heating parameters + setPreTreatmentHeatingParams( targetTempC, FILL_RESERVOIR_TO_VOLUME_ML, DEFAULT_TARGET_FILL_FLOW_RATE_LPM, dialysateFlowMLPM ); state = PRE_TREATMENT_RESERVOIR_MGMT_COMPLETE_STATE; } else @@ -1566,6 +1597,142 @@ /*********************************************************************//** * @brief + * The execPreTreatmentTestConfigReservoirMgmt function executes the state + * machine for reservoir management during pre-treatment mode when a test + * configuration (expedite pre-treatment test config for now) is enabled. + * @details Inputs: currentReservoirMgmtState + * @details Outputs: currentReservoirMgmtState + * @return none + *************************************************************************/ +static void execPreTreatmentTestConfigReservoirMgmt( void ) +{ + DG_SWITCH_RSRVRS_CMD_T rsrvrCmd; + DG_CMD_RESPONSE_T dgCmdResp; + F32 reservoir1Level = getReservoirWeight( DG_RESERVOIR_1 ); + F32 reservoir2Level = getReservoirWeight( DG_RESERVOIR_2 ); + DG_OP_MODE_T dgOpMode = getDGOpMode(); + U32 dgSubMode = getDGSubMode(); + + switch( currentReservoirMgmtState ) + { + case PRE_TREATMENT_RESERVOIR_MGMT_START_STATE: + rsrvrCmd.useLastTrimmerHeaterDC = FALSE; + + if ( ( reservoir1Level >= PRE_TREATMENT_TEST_CONFIG_MIN_RSRVR_VOL_ML ) && ( reservoir1Level < PRE_TREATMENT_TEST_CONFIG_MAX_RSRVR_VOL_ML ) ) + { + // Assume a reservoir switch is not needed and transition to the complete state because we are done + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_COMPLETE_STATE; + + if ( DG_RESERVOIR_2 == getDGActiveReservoir() ) + { + // Reservoir 1 has the right volume, set it to active reservoir and wait for it to be done + rsrvrCmd.reservoirID = (U32)DG_RESERVOIR_1; + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_WAIT_FOR_RESERVOIR_SWITCH_STATE; + cmdSetDGActiveReservoir( &rsrvrCmd ); + } + } + else if ( reservoir1Level >= PRE_TREATMENT_TEST_CONFIG_MAX_RSRVR_VOL_ML ) + { + // Reservoir 1 needs a partial drain so set it to be inactive so DG can drain it + if ( DG_RESERVOIR_1 == getDGActiveReservoir() ) + { + rsrvrCmd.reservoirID = (U32)DG_RESERVOIR_2; + cmdSetDGActiveReservoir( &rsrvrCmd ); + } + + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_DRAIN_CMD_STATE; + } + else if ( ( reservoir2Level >= PRE_TREATMENT_TEST_CONFIG_MIN_RSRVR_VOL_ML ) && ( reservoir2Level < PRE_TREATMENT_TEST_CONFIG_MAX_RSRVR_VOL_ML ) ) + { + // Reservoir 2 is in the right level, just make sure it is the active reservoir + // Assume a reservoir switch is not needed and transition to the complete state because we are done + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_COMPLETE_STATE; + + if ( DG_RESERVOIR_1 == getDGActiveReservoir() ) + { + rsrvrCmd.reservoirID = (U32)DG_RESERVOIR_2; + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_WAIT_FOR_RESERVOIR_SWITCH_STATE; + cmdSetDGActiveReservoir( &rsrvrCmd ); + } + } + else if ( reservoir2Level >= PRE_TREATMENT_TEST_CONFIG_MAX_RSRVR_VOL_ML ) + { + if ( DG_RESERVOIR_2 == getDGActiveReservoir() ) + { + rsrvrCmd.reservoirID = (U32)DG_RESERVOIR_1; + cmdSetDGActiveReservoir( &rsrvrCmd ); + } + + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_DRAIN_CMD_STATE; + } + break; + + case PRE_TREATMENT_RESERVOIR_MGMT_DRAIN_CMD_STATE: + // If DG has not started yet, start DG + if ( DG_MODE_STAN == dgOpMode ) + { + cmdStartDG(); + } + + // Ensure any pending reservoir switches are completed before sending drain command + if ( TRUE == hasDGCompletedReservoirSwitch() ) + { + if ( ( DG_MODE_GENE == dgOpMode ) && ( DG_GEN_IDLE_MODE_STATE_FLUSH_WATER == dgSubMode ) ) + { + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_DRAIN_CMD_RESP_STATE; + cmdStartDGDrain( PRE_TREATMENT_FULL_RESERVOIR_VOLUME_ML, FALSE, FALSE, TRUE ); + } + } + break; + + case PRE_TREATMENT_RESERVOIR_MGMT_DRAIN_CMD_RESP_STATE: + // Check DG response to drain command + if ( TRUE == getDGCommandResponse( DG_CMD_START_DRAIN, &dgCmdResp ) ) + { + if ( DG_CMD_REQUEST_REJECT_REASON_NONE == dgCmdResp.rejectCode ) + { + if ( DG_MODE_DRAI == dgOpMode ) + { + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_REQUEST_RESERVOIR_SWITCH_STATE; + } + } + else + { + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_DRAIN_CMD_STATE; + } + } + break; + + case PRE_TREATMENT_RESERVOIR_MGMT_REQUEST_RESERVOIR_SWITCH_STATE: + if ( ( DG_MODE_GENE == dgOpMode ) && ( DG_GEN_IDLE_MODE_STATE_FLUSH_WATER == dgSubMode ) ) + { + DG_SWITCH_RSRVRS_CMD_T rsrvrCmd; + DG_RESERVOIR_ID_T inactiveReservoir = getDGInactiveReservoir(); + + rsrvrCmd.reservoirID = ( DG_RESERVOIR_1 == inactiveReservoir ? (U32)DG_RESERVOIR_1 : (U32)DG_RESERVOIR_2 ); + rsrvrCmd.useLastTrimmerHeaterDC = FALSE; + + cmdSetDGActiveReservoir( &rsrvrCmd ); + + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_WAIT_FOR_RESERVOIR_SWITCH_STATE; + } + break; + + case PRE_TREATMENT_RESERVOIR_MGMT_WAIT_FOR_RESERVOIR_SWITCH_STATE: + if ( TRUE == hasDGCompletedReservoirSwitch() ) + { + currentReservoirMgmtState = PRE_TREATMENT_RESERVOIR_MGMT_COMPLETE_STATE; + } + break; + + case PRE_TREATMENT_RESERVOIR_MGMT_COMPLETE_STATE: + // Done with test configuration reservoir management. Do nothing. + break; + } +} + +/*********************************************************************//** + * @brief * The testSetPreTreatmentModePublishIntervalOverride function sets the override of the * pre-treatment mode data publication interval. * @details Inputs: none