Index: firmware/App/Drivers/BubbleDetector.h =================================================================== diff -u -r37d4284f56e175716ea13ae56c621110fa96e53c -r494b19c85bdea2b8fc273c648b4f1955f9d07dc3 --- firmware/App/Drivers/BubbleDetector.h (.../BubbleDetector.h) (revision 37d4284f56e175716ea13ae56c621110fa96e53c) +++ firmware/App/Drivers/BubbleDetector.h (.../BubbleDetector.h) (revision 494b19c85bdea2b8fc273c648b4f1955f9d07dc3) @@ -18,7 +18,7 @@ #ifndef __BUBBLE_DETECTOR_H__ #define __BUBBLE_DETECTOR_H__ -#include "TDCommon.h" +#include "TDCommon.h" /** * @defgroup BubbleDetector BubbleDetector Index: firmware/App/Monitors/Bubbles.c =================================================================== diff -u --- firmware/App/Monitors/Bubbles.c (revision 0) +++ firmware/App/Monitors/Bubbles.c (revision 494b19c85bdea2b8fc273c648b4f1955f9d07dc3) @@ -0,0 +1,364 @@ +/************************************************************************** +* +* Copyright (c) 2024-2024 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 Bubbles.c +* +* @author (last) Sean +* @date (last) 07-Aug-2024 +* +* @author (original) Sean +* @date (original) 07-Aug-2024 +* +***************************************************************************/ + +#include "AlarmMgmtTD.h" +#include "Bubbles.h" +#include "FpgaTD.h" +#include "Messaging.h" +#include "OperationModes.h" +#include "TaskGeneral.h" +#include "TaskPriority.h" +#include "Timers.h" + +/** + * @addtogroup Bubbles + * @{ + */ + +// ********** private definitions ********** + +#define BUBBLE_PUB_INTERVAL ( MS_PER_SECOND / TASK_PRIORITY_INTERVAL ) ///< Interval (ms/task time) at which the air bubble detector data is published on the CAN bus. +#define BUBBLE_TIMEOUT_MS 500 ///< Air bubble detector timeout for self-test (15 ms extended edge detection) +#define DATA_PUBLISH_COUNTER_START_COUNT 70 ///< Data publish counter start count. + +/// Defined states for the air bubble detectors state machine. +typedef enum BubbleStates +{ + BUBBLE_NORMAL_STATE = 0, ///< Normal state + BUBBLE_SELF_TEST_STATE, ///< Self-test state + NUM_OF_BUBBLE_STATES ///< Number of bubble detector states +} BUBBLE_STATES_T; + +// ********** private data ********** + +static BUBBLE_STATES_T bubblesState[ NUM_OF_BUBBLE_DETECTORS ]; ///< Current state of air bubble detectors state machines. +static SELF_TEST_STATUS_T bubblesSelfTestStatus[ NUM_OF_BUBBLE_DETECTORS ]; ///< Current status of air bubble detectors self-tests. + +static U32 bubblesSelfTestStartTime[ NUM_OF_BUBBLE_DETECTORS ]; ///< Air bubble detectors self-test start times. +static BOOL bubblesSelfTestRequested[ NUM_OF_BUBBLE_DETECTORS ]; ///< Air bubble detectors self-test requested flags. +static BOOL bubbleDetectionEnabled[ NUM_OF_BUBBLE_DETECTORS ]; ///< Flag indicates whether air bubble alarm detection is enabled. + +static OVERRIDE_U32_T bubblesDataPublishInterval = { BUBBLE_PUB_INTERVAL, BUBBLE_PUB_INTERVAL, 0, 0 }; ///< Interval (in ms) at which to publish air bubble detectors data on CAN bus. +static U32 bubblesDataPublicationTimerCounter; ///< Timer counter used to schedule air bubble detectors data publication to CAN bus. + +// ********** private function prototypes ********** + +static BUBBLE_STATES_T handleBubbleNormalState( BUBBLE_DETECTOR_T bubble ); +static BUBBLE_STATES_T handleBubbleSelfTestState( BUBBLE_DETECTOR_T bubble ); + +static void publishBubblesData( void ); + +/*********************************************************************//** + * @brief + * The initBubbles function initializes the air bubble detectors module. + * @details \b Inputs: none + * @details \b Outputs: Air bubble monitor unit initialized. + * @return none + *************************************************************************/ +void initBubbles( void ) +{ + BUBBLE_DETECTOR_T bubble; + + // initialize low-level driver + initBubbleDetector(); + + // initialize unit data + for ( bubble = (BUBBLE_DETECTOR_T)0; bubble < NUM_OF_BUBBLE_DETECTORS; bubble++ ) + { + bubblesState[ bubble ] = BUBBLE_NORMAL_STATE; + bubblesSelfTestStatus[ bubble ] = SELF_TEST_STATUS_IN_PROGRESS; + bubblesSelfTestRequested[ bubble ] = FALSE; + bubblesSelfTestStartTime[ bubble ] = 0; + bubbleDetectionEnabled[ bubble ] = TRUE; + } + + bubblesDataPublicationTimerCounter = DATA_PUBLISH_COUNTER_START_COUNT; +} + +/*********************************************************************//** + * @brief + * The execBubbles function executes the air bubble monitor state machine. + * @details \b Inputs: bubblesState + * @details \b Outputs: bubblesState + * @return none + *************************************************************************/ +void execBubbles( void ) +{ + BUBBLE_DETECTOR_T bubble; + + // Read all bubble detectors + readBubbleDetectors(); + + if ( getCurrentOperationMode() != MODE_INIT ) + { + // Loop through all of the air bubble detectors + for ( bubble = (BUBBLE_DETECTOR_T)0; bubble < NUM_OF_BUBBLE_DETECTORS; bubble++ ) + { + // Execute the air bubble detector state machine + switch( bubblesState[ bubble ] ) + { + case BUBBLE_NORMAL_STATE: + bubblesState[ bubble ] = handleBubbleNormalState( bubble ); + break; + + case BUBBLE_SELF_TEST_STATE: + bubblesState[ bubble ] = handleBubbleSelfTestState( bubble ); + break; + + default: + SET_ALARM_WITH_2_U32_DATA( ALARM_ID_TD_SOFTWARE_FAULT, SW_FAULT_ID_BUBBLES_INVALID_STATE, bubblesState[ bubble ] ) + break; + } + } + } + + // Publish air bubble detectors data if due + publishBubblesData(); +} + +/*********************************************************************//** + * @brief + * The setVenousBubbleDetectionEnabled function enabled or disables venous + * bubble detection. + * @details \b Inputs: none + * @details \b Outputs: bubbleDetectionEnabled[] + * @param bubble ID of bubble detector to set enabled status for + * @param enabled flag indicates whether bubble detection is enabled for the + * given bubble detector + * @return none + *************************************************************************/ +void setVenousBubbleDetectionEnabled( BUBBLE_DETECTOR_T bubble, BOOL enabled ) +{ + bubbleDetectionEnabled[ bubble ] = enabled; +} + +/*********************************************************************//** + * @brief + * The getVenousBubbleDetectionEnabled function returns the state of the + * given bubble detector's enable flag. + * @details \b Inputs: bubbleDetectionEnabled[] + * @details \b Outputs: none + * @param bubble ID of bubble detector to get enabled status for + * @return TRUE if given bubble detector is enabled, FALSE if not + *************************************************************************/ +BOOL getVenousBubbleDetectionEnabled( BUBBLE_DETECTOR_T bubble ) +{ + return bubbleDetectionEnabled[ bubble ]; +} + +/*********************************************************************//** + * @brief + * The selfTestBubble function requests that a specified air bubble detector + * be self-tested. + * @details Inputs: none + * @details Outputs: bubblesSelfTestRequested + * @param bubble ID of bubble detector to request self-test for + * @return none + *************************************************************************/ +void selfTestBubble( BUBBLE_DETECTOR_T bubble ) +{ + bubblesSelfTestRequested[ bubble ] = TRUE; +} + +/*********************************************************************//** + * @brief + * The getBubbleSelfTestStatus function gets the status for a given air bubble + * detector self-test. + * @details \b Inputs: bubblesSelfTestStatus + * @details \b Outputs: none + * @param bubble ID of bubble detector to get self-test status for + * @return status of air bubble detector self-test. + *************************************************************************/ +SELF_TEST_STATUS_T getBubbleSelfTestStatus( BUBBLE_DETECTOR_T bubble ) +{ + return bubblesSelfTestStatus[ bubble ]; +} + +/*********************************************************************//** + * @brief + * The handleBubbleNormalState function handles a given air bubble module + * in normal state. + * @details \b Alarm: ALARM_ID_HD_VENOUS_BUBBLE_DETECTED if venous bubble detected. + * @details \b Alarm: ALARM_ID_TD_SOFTWARE_FAULT if given bubble sensor is invalid. + * @details \b Inputs: none + * @details \b Outputs: bubblesSelfTestStatus + * @param bubble ID of bubble detector to execute normal state for + * @return next state + *************************************************************************/ +static BUBBLE_STATES_T handleBubbleNormalState( BUBBLE_DETECTOR_T bubble ) +{ + BUBBLE_STATES_T state = BUBBLE_NORMAL_STATE; +// TREATMENT_STATE_T treatmentState = getTreatmentState(); + + if ( bubble < NUM_OF_BUBBLE_DETECTORS ) + { + // check for bubble detection +#ifndef _RELEASE_ +// if ( getSoftwareConfigStatus( SW_CONFIG_DISABLE_BUBBLE_ALARMS ) != SW_CONFIG_ENABLE_VALUE ) +#endif + { + // Check for venous bubble alarm if enabled. + if ( ( BUBBLE_DETECTED == getBubbleDetectedState( bubble ) ) && + ( bubbleDetectionEnabled[ bubble ] != FALSE ) ) + { +// activateAlarmNoData( ALARM_ID_HD_VENOUS_BUBBLE_DETECTED ); + } + } + + // if self-test requested, initiate self-test + if ( TRUE == bubblesSelfTestRequested[ bubble ] ) + { + state = BUBBLE_SELF_TEST_STATE; + bubblesSelfTestRequested[ bubble ] = FALSE; + bubblesSelfTestStatus[ bubble ] = SELF_TEST_STATUS_IN_PROGRESS; + + if ( BUBBLE_DETECTOR_ADV == bubble ) + { + setFPGAVenousBubbleSelfTest(); + } + bubblesSelfTestStartTime[ bubble ] = getMSTimerCount(); + } + } + else + { + SET_ALARM_WITH_2_U32_DATA( ALARM_ID_TD_SOFTWARE_FAULT, SW_FAULT_ID_BUBBLES_INVALID_SENSOR_ID1, bubble ) + } + + return state; +} + +/*********************************************************************//** + * @brief + * The handleBubbleSelfTestState function handles a given air bubble detector + * in self-test state. + * @details \b Alarm: ALARM_ID_TD_SOFTWARE_FAULT if given bubble sensor is invalid. + * @details \b Inputs: bubblesSelfTestStatus + * @details \b Outputs: bubblesSelfTestStatus + * @param bubble ID of bubble detector to execute self-test state for + * @return next state + *************************************************************************/ +static BUBBLE_STATES_T handleBubbleSelfTestState( BUBBLE_DETECTOR_T bubble ) +{ + BUBBLE_STATES_T state = BUBBLE_SELF_TEST_STATE; + + if ( bubble < NUM_OF_BUBBLE_DETECTORS ) + { + if ( SELF_TEST_STATUS_IN_PROGRESS == bubblesSelfTestStatus[ bubble ] ) + { + if ( BUBBLE_DETECTED == getBubbleDetectedState( bubble ) ) // Faked air bubble caused + { + bubblesSelfTestStatus[ bubble ] = SELF_TEST_STATUS_PASSED; + if ( BUBBLE_DETECTOR_ADV == bubble ) + { + clearFPGAVenousBubbleSelfTest(); + } + } + else if ( TRUE == didTimeout( bubblesSelfTestStartTime[ bubble ], BUBBLE_TIMEOUT_MS ) ) + { + bubblesSelfTestStatus[ bubble ] = SELF_TEST_STATUS_FAILED; +// activateAlarmNoData( ALARM_ID_TD_VENOUS_BUBBLE_SELF_TEST_FAILURE ); + } + } + else + { + // Air bubble self-test finished, wait for self-test faked air bubble detector clear + if ( ( NO_BUBBLE_DETECTED == getBubbleDetectedState( bubble ) ) || + ( TRUE == didTimeout( bubblesSelfTestStartTime[ bubble ], BUBBLE_TIMEOUT_MS + 100 ) ) ) + { + state = BUBBLE_NORMAL_STATE; + } + } + } + else + { + SET_ALARM_WITH_2_U32_DATA( ALARM_ID_TD_SOFTWARE_FAULT, SW_FAULT_ID_BUBBLES_INVALID_SENSOR_ID2, bubble ) + } + + return state; +} + +/*********************************************************************//** + * @brief + * The publishBubblesData function publishes air bubble detectors data at + * the set interval. + * @details \b Inputs: status, bubblesState + * @details \b Outputs: if broadcast is due, send air bubble detectors data + * @return none + *************************************************************************/ +static void publishBubblesData( void ) +{ + // Publish air bubble detectors data on interval + if ( ++bubblesDataPublicationTimerCounter >= getU32OverrideValue( &bubblesDataPublishInterval ) ) + { + BUBBLES_DATA_T bubbleData; + + bubbleData.statusADV = (U32)getBubbleDetectedState( BUBBLE_DETECTOR_ADV ); + bubbleData.stateADV = (U32)bubblesState[ BUBBLE_DETECTOR_ADV ]; + broadcastData( MSG_ID_TD_BUBBLES_DATA, COMM_BUFFER_OUT_CAN_TD_BROADCAST, (U08*)&bubbleData, sizeof( BUBBLES_DATA_T ) ); + bubblesDataPublicationTimerCounter = 0; + } +} + + +/************************************************************************* + * TEST SUPPORT FUNCTIONS + *************************************************************************/ + + +/*********************************************************************//** + * @brief + * The testBubblesDataPublishIntervalOverride function overrides the interval + * at which the TD bubbles data is published. + * @details \b Inputs: none + * @details \b Outputs: bubblesDataPublishInterval + * @param message Override message from Dialin which includes the interval + * (in ms) to override the bubbles data broadcast interval to. + * @return TRUE if override request is successful, FALSE if not + *************************************************************************/ +BOOL testBubblesDataPublishIntervalOverride( MESSAGE_T *message ) +{ + BOOL result = FALSE; + TEST_OVERRIDE_PAYLOAD_T override; + OVERRIDE_TYPE_T ovType = getOverridePayloadFromMessage( message, &override ); + + // Verify tester has logged in with TD and override type is valid + if ( ( TRUE == isTestingActivated() ) && ( ovType != OVERRIDE_INVALID ) && ( ovType < NUM_OF_OVERRIDE_TYPES ) ) + { + if ( OVERRIDE_OVERRIDE == ovType ) + { + U32 value = override.state.u32; + U32 intvl = value / TASK_GENERAL_INTERVAL; + + if ( intvl > 0 ) + { + result = TRUE; + bubblesDataPublishInterval.ovData = intvl; + bubblesDataPublishInterval.override = OVERRIDE_KEY; + } + } + else + { + result = TRUE; + bubblesDataPublishInterval.override = OVERRIDE_RESET; + bubblesDataPublishInterval.ovData = bubblesDataPublishInterval.ovInitData; + } + } + + return result; +} + +/**@}*/ Index: firmware/App/Monitors/Bubbles.h =================================================================== diff -u --- firmware/App/Monitors/Bubbles.h (revision 0) +++ firmware/App/Monitors/Bubbles.h (revision 494b19c85bdea2b8fc273c648b4f1955f9d07dc3) @@ -0,0 +1,59 @@ +/************************************************************************** +* +* Copyright (c) 2024-2024 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 Bubbles.h +* +* @author (last) Sean +* @date (last) 07-Aug-2024 +* +* @author (original) Sean +* @date (original) 07-Aug-2024 +* +***************************************************************************/ + +#ifndef __BUBBLES_H__ +#define __BUBBLES_H__ + +#include "TDCommon.h" +#include "BubbleDetector.h" + +/** + * @defgroup Bubbles Bubbles + * @brief Air bubble detectors monitor module. Monitors the + * bubble detector. + * + * SMD - Venous Air Bubble Detector Part No. DIA8413 + * + * @addtogroup Bubbles + * @{ + */ + +// ********** public definitions ********** + +/// Bubble detectors data publish +typedef struct +{ + U32 statusADV; ///< Venous bubble detector status + U32 stateADV; ///< Venous bubble detector state +} BUBBLES_DATA_T; + +// ********** public function prototypes ********** + +void initBubbles( void ); +void execBubbles( void ); +void selfTestBubble( BUBBLE_DETECTOR_T ); + +void setVenousBubbleDetectionEnabled( BUBBLE_DETECTOR_T bubble, BOOL enabled ); +BOOL getVenousBubbleDetectionEnabled( BUBBLE_DETECTOR_T bubble ); + +SELF_TEST_STATUS_T getBubbleSelfTestStatus( BUBBLE_DETECTOR_T bubble ); + +BOOL testBubblesDataPublishIntervalOverride( MESSAGE_T *message ); + +/**@}*/ + +#endif Index: firmware/App/Services/AlarmMgmtSWFaults.h =================================================================== diff -u -r8cbddbe34a4ffed5a4d9fac07a065799c5862611 -r494b19c85bdea2b8fc273c648b4f1955f9d07dc3 --- firmware/App/Services/AlarmMgmtSWFaults.h (.../AlarmMgmtSWFaults.h) (revision 8cbddbe34a4ffed5a4d9fac07a065799c5862611) +++ firmware/App/Services/AlarmMgmtSWFaults.h (.../AlarmMgmtSWFaults.h) (revision 494b19c85bdea2b8fc273c648b4f1955f9d07dc3) @@ -111,6 +111,9 @@ SW_FAULT_ID_PRESSURE_SENSOR_INVALID_SENSOR4 = 80, SW_FAULT_ID_VOLTAGES_INVALID_STATE = 81, SW_FAULT_ID_VOLTAGES_INVALID_SIGNAL = 82, + SW_FAULT_ID_BUBBLES_INVALID_STATE = 83, + SW_FAULT_ID_BUBBLES_INVALID_SENSOR_ID1 = 84, + SW_FAULT_ID_BUBBLES_INVALID_SENSOR_ID2 = 84, NUM_OF_SW_FAULT_IDS } SW_FAULT_ID_T; Index: firmware/App/Services/Messaging.c =================================================================== diff -u -r2f00c73cb1a67b9206c64a29a4d45d21b0f129f2 -r494b19c85bdea2b8fc273c648b4f1955f9d07dc3 --- firmware/App/Services/Messaging.c (.../Messaging.c) (revision 2f00c73cb1a67b9206c64a29a4d45d21b0f129f2) +++ firmware/App/Services/Messaging.c (.../Messaging.c) (revision 494b19c85bdea2b8fc273c648b4f1955f9d07dc3) @@ -17,7 +17,7 @@ #include // For memcpy() -#include "BubbleDetector.h" +#include "Bubbles.h" #include "Compatible.h" #include "Messaging.h" #include "OperationModes.h" @@ -73,7 +73,8 @@ MSG_ID_TD_SOFTWARE_RESET_REQUEST, MSG_ID_TD_VENOUS_BUBBLE_OVERRIDE_REQUEST, MSG_ID_TD_VOLTAGE_PUBLISH_INTERVAL_OVERRIDE_REQUEST, - MSG_ID_TD_VOLTAGE_OVERRIDE_REQUEST + MSG_ID_TD_VOLTAGE_OVERRIDE_REQUEST, + MSG_ID_TD_BUBBLE_PUBLISH_INTERVAL_OVERRIDE_REQUEST }; /// Message handling function table @@ -82,7 +83,8 @@ &handleTDSoftwareResetRequest, &testBubbleDetectOverride, &testVoltageDataPublishIntervalOverride, - &testVoltageOverride + &testVoltageOverride, + &testBubblesDataPublishIntervalOverride }; #define NUM_OF_FUNCTION_HANDLERS (sizeof(MSG_FUNCTION_HANDLERS) / sizeof(MsgFuncPtr)) Index: firmware/App/Tasks/TaskPriority.c =================================================================== diff -u -r380b0afc95467d0861ff3aa2cdcde5d5d7ac85e7 -r494b19c85bdea2b8fc273c648b4f1955f9d07dc3 --- firmware/App/Tasks/TaskPriority.c (.../TaskPriority.c) (revision 380b0afc95467d0861ff3aa2cdcde5d5d7ac85e7) +++ firmware/App/Tasks/TaskPriority.c (.../TaskPriority.c) (revision 494b19c85bdea2b8fc273c648b4f1955f9d07dc3) @@ -15,6 +15,7 @@ * ***************************************************************************/ +#include "Bubbles.h" #include "FPGA.h" #include "SystemCommTD.h" #include "TaskPriority.h" @@ -69,8 +70,8 @@ // Monitor blood pump and flow // execBloodFlowMonitor(); - // Monitor air bubble detector -// execBubble(); + // Monitor air bubble detectors + execBubbles(); // 2nd pass for FPGA execFPGA( FALSE ); Index: firmware/source/sys_main.c =================================================================== diff -u -r8cbddbe34a4ffed5a4d9fac07a065799c5862611 -r494b19c85bdea2b8fc273c648b4f1955f9d07dc3 --- firmware/source/sys_main.c (.../sys_main.c) (revision 8cbddbe34a4ffed5a4d9fac07a065799c5862611) +++ firmware/source/sys_main.c (.../sys_main.c) (revision 494b19c85bdea2b8fc273c648b4f1955f9d07dc3) @@ -64,7 +64,7 @@ #include "TDCommon.h" #include "AlarmLamp.h" -#include "BubbleDetector.h" +#include "Bubbles.h" #include "CpldInterface.h" #include "DDInterface.h" #include "FpgaTD.h" @@ -174,7 +174,6 @@ // Initialize drivers initInternalADC(); // initBattery(); - initBubbleDetector(); initPressureSensor(); // Initialize async interrupt handlers initInterrupts(); @@ -189,6 +188,7 @@ initSystemCommTD(); initWatchdogMgmt(); // Initialize monitors + initBubbles(); initVoltagesMonitor(); // Initialize controllers initAlarmLamp();