Index: firmware/App/Modes/ModeTreatment.c =================================================================== diff -u -rda59fa4a98dbc11c37677e92a66aa940d251678f -r4f7855d894ddf2b62e7225050b5137d01862dd4b --- firmware/App/Modes/ModeTreatment.c (.../ModeTreatment.c) (revision da59fa4a98dbc11c37677e92a66aa940d251678f) +++ firmware/App/Modes/ModeTreatment.c (.../ModeTreatment.c) (revision 4f7855d894ddf2b62e7225050b5137d01862dd4b) @@ -7,8 +7,8 @@ * * @file ModeTreatment.c * -* @author (last) Raghu Kallala -* @date (last) 04-May-2026 +* @author (last) Praneeth Bunne +* @date (last) 04-Jun-2026 * * @author (original) Sean Nash * @date (original) 21-Apr-2025 @@ -17,9 +17,11 @@ #include "AirTrap.h" //#include "BloodFlow.h" +#include "BPModule.h" #include "Bubbles.h" #include "Buttons.h" #include "DDInterface.h" +#include "FluidBolus.h" #include "Messaging.h" #include "ModeService.h" #include "ModeTreatment.h" @@ -53,8 +55,6 @@ #define TREATMENT_SETTINGS_RANGES_PUB_INTERVAL ( ( 60 * MS_PER_SECOND ) / TASK_GENERAL_INTERVAL ) /// Ultrafiltration data broadcast interval (ms/task time) count. #define ULTRAFILTRATION_DATA_PUB_INTERVAL ( MS_PER_SECOND / TASK_GENERAL_INTERVAL ) -/// Saline bolus data broadcast interval (ms/task time) count. // TODO - move to StateTxSalineBolus.c when implemented -#define SALINE_BOLUS_DATA_PUB_INTERVAL ( MS_PER_SECOND / TASK_GENERAL_INTERVAL ) /// Macro to calculate the elapsed treatment time in seconds. #define CALC_ELAPSED_TREAT_TIME_IN_SECS() ( treatmentTimeMS / MS_PER_SECOND ) @@ -72,7 +72,7 @@ static BOOL treatmentCompleted; ///< Flag indicates whether the treatment has completed. static U32 presTreatmentTimeSecs; ///< Prescribed treatment time (in seconds). -static F32 presUFVolumeMl; ///< Prescribed ultrafiltration volume (in L). +static F32 presUFVolumeMl; ///< Prescribed ultrafiltration volume (in Ml). static F32 presUFRateMlMin; ///< Prescribed ultrafiltration rate (in mL/Min). static U32 treatmentTimeMS; ///< Elapsed treatment time (in ms). @@ -81,7 +81,6 @@ static U32 treatmentStateBroadcastTimerCtr; ///< Treatment state 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. static U32 ultrafiltrationBroadcastTimerCtr; ///< Ultrafiltration data broadcast timer counter used to schedule when to transmit data. -static U32 salineBolusBroadcastTimerCtr; ///< Saline bolus data broadcast timer counter used to schedule when to transmit data. /// Interval (in task intervals) at which to publish alarm status to CAN bus. static OVERRIDE_U32_T treatmentTimePublishInterval; @@ -104,15 +103,13 @@ static void broadcastTreatmentSettingsRanges( void ); static void broadcastTreatmentPeriodicData(); -static void publishSalineBolusData( void ); // TODO - move to StateTxSalineBolus.c when implemented static void publishUltrafiltrationData( void ); static U32 getMinTreatmentTimeInMinutes( void ); static TREATMENT_STATE_T handleTreatmentStartState( void ); static TREATMENT_STATE_T handleTreatmentBloodPrimeState( void ); static TREATMENT_STATE_T handleTreatmentDialysisState( void ); static TREATMENT_STATE_T handleTreatmentIsoUFState( void ); static TREATMENT_STATE_T handleTreatmentDialysatePausedState( void ); -static TREATMENT_STATE_T handleTreatmentSalineBolusState( void ); static TREATMENT_STATE_T handleTreatmentPausedState( void ); static TREATMENT_STATE_T handleTreatmentRinsebackState( void ); static TREATMENT_STATE_T handleTreatmentRecircState( void ); @@ -155,7 +152,6 @@ treatmentStateBroadcastTimerCtr = TREATMENT_STATE_DATA_PUB_INTERVAL; // So we send state data immediately when we begin treatment mode treatmentParamsRangesBroadcastTimerCtr = TREATMENT_SETTINGS_RANGES_PUB_INTERVAL; // So we send ranges immediately when we begin treatment mode ultrafiltrationBroadcastTimerCtr = ULTRAFILTRATION_DATA_PUB_INTERVAL; // So we send ultrafiltration immediately when we begin treatment mode - salineBolusBroadcastTimerCtr = SALINE_BOLUS_DATA_PUB_INTERVAL; // So we send saline bolus data immediately when we begin treatment mode presTreatmentTimeSecs = 0; presUFVolumeMl = 0.0F; @@ -193,6 +189,7 @@ // initRinseback(); // initTreatmentRecirc(); // initTreatmentEnd(); + initFluidBolus(); // Started the treatment - set the start time in epoch // setTxLastStartTimeEpoch( getRTCTimestamp() ); @@ -467,10 +464,6 @@ // currentTreatmentState = handleTreatmentIsoUFState(); // break; // -// case TREATMENT_SALINE_BOLUS_STATE: -// currentTreatmentState = handleTreatmentSalineBolusState(); -// break; -// // case TREATMENT_DIALYSATE_PAUSED_STATE: // currentTreatmentState = handleTreatmentDialysatePausedState(); // break; @@ -507,12 +500,13 @@ broadcastTreatmentPeriodicData(); // Publish ultrafiltration data at set interval (whether we are performing UF or not) publishUltrafiltrationData(); - // Publish saline bolus data at set interval (whether we are delivering one or not) - publishSalineBolusData(); // Manage air trap control execAirTrapMonitorTreatment(); + // Call fluid bolus + execFluidBolus(); + return currentTreatmentState; } @@ -627,10 +621,15 @@ U32 msSinceLast = calcTimeBetween( lastTreatmentTimeStamp, newTime ); DIALYSIS_STATE_T dialysisState = getDialysisState(); - // Update treatment time - treatmentTimeMS += msSinceLast; + // Always update timestamp to avoid time jump on bolus exit lastTreatmentTimeStamp = newTime; + // Only update treatment time when fluid bolus is not active + if ( FALSE == isFluidBolusActive() ) + { + treatmentTimeMS += msSinceLast; + } + // End treatment if treatment duration has been reached if ( CALC_ELAPSED_TREAT_TIME_IN_SECS() >= presTreatmentTimeSecs ) { @@ -915,14 +914,32 @@ payload.rinsebackState = 0; // getCurrentRinsebackState(); payload.txRecircState = 0; // getCurrentTreatmentRecircState(); payload.txEndState = 0; // getCurrentTreatmentEndState(); - payload.txSalBolusState = 0; // + payload.txFluidBolusState = getCurrentFluidBolusState(); payload.txHepState = 0; // broadcastData( MSG_ID_TD_TREATMENT_STATE_DATA, COMM_BUFFER_OUT_CAN_TD_BROADCAST, (U08*)(&payload), sizeof( TREATMENT_STATE_DATA_T ) ); } } /*********************************************************************//** * @brief + * The updateTreatmentBroadcastData function updates treatment broadcast + * data values used for treatment time and ultrafiltration broadcasts. + * @details \b Inputs: none. + * @details \b Outputs: presTreatmentTimeSecs, presUFVolumeMl, presUFRateMlMin. + * @param ufRateLhr ultrafiltration rate in L/hr. + * @return none. + *************************************************************************/ +void updateTreatmentBroadcastData( F32 ufRateLhr ) +{ + presTreatmentTimeSecs = getTreatmentParameterU32( TREATMENT_PARAM_TREATMENT_DURATION ) * SEC_PER_MIN; + + presUFVolumeMl = getTreatmentParameterF32( TREATMENT_PARAM_UF_VOLUME ); + + presUFRateMlMin = ( ufRateLhr * (F32)ML_PER_LITER ) / (F32)MIN_PER_HOUR; +} + +/*********************************************************************//** + * @brief * The broadcastTreatmentSettingsRanges function computes and broadcasts * updated treatment parameter ranges that the user may change during treatment. * It is assumed that prescription settings have already been set prior to calling @@ -991,7 +1008,7 @@ // F32 const arterialPres = getFilteredArterialPressure(); // F32 const venousPres = getFilteredVenousPressure(); // -// if ( ( TREATMENT_DIALYSIS_STATE == getTreatmentState() ) && ( getDialysisState() != DIALYSIS_SALINE_BOLUS_STATE ) ) +// if ( ( TREATMENT_DIALYSIS_STATE == getTreatmentState() ) && ( getTreatmentState() != TREATMENT_SALINE_BOLUS_STATE ) ) // { // treatmentBloodFlowRateTotal_mL_min += getMeasuredBloodFlowRate(); // treatmentDialysateFlowRateTotal_mL_min += getMeasuredDialInFlowRate(); @@ -1102,30 +1119,6 @@ /*********************************************************************//** * @brief - * The publishSalineBolusData function publishes the saline bolus data - * at the set time interval. - * @details \b Inputs: none - * @details \b Outputs: none - * @param dialysisState next dialysis state - * @return next saline bolus state - *************************************************************************/ -static void publishSalineBolusData( void ) -{ - if ( ++salineBolusBroadcastTimerCtr >= SALINE_BOLUS_DATA_PUB_INTERVAL ) - { - SALINE_BOLUS_DATA_PAYLOAD_T data; - - data.tgtSalineVolumeMl = getTreatmentParameterU32( TREATMENT_PARAM_FLUID_BOLUS_VOLUME ); - data.cumSalineVolumeMl = 0.0F; // TODO - data.bolSalineVolumeMl = 0.0F; // TODO - - sendMessage( MSG_ID_TD_SALINE_BOLUS_DATA, COMM_BUFFER_OUT_CAN_TD_BROADCAST, (U08*)(&data), sizeof( SALINE_BOLUS_DATA_PAYLOAD_T ) ); - salineBolusBroadcastTimerCtr = 0; - } -} - -/*********************************************************************//** - * @brief * The publishUltrafiltrationData function publishes the ultrafiltration data * at the set time interval. * @details \b Inputs: none @@ -1142,7 +1135,7 @@ presUFRateLHr = presUFVolumeL / ( (F32)getTreatmentParameterU32( TREATMENT_PARAM_TREATMENT_DURATION ) / (F32)MIN_PER_HOUR ); data.setUFVolumeL = presUFVolumeL; - data.tgtUFRateLHr = presUFRateLHr; + data.tgtUFRateLHr = ( presUFRateMlMin * (F32)MIN_PER_HOUR ) / (F32)ML_PER_LITER; data.ufVolumeDeliveredL = getUltrafiltrationVolumeDrawn(); data.ufState = (U32)getDialysisState();