Index: firmware/App/Controllers/TemperatureSensors.c =================================================================== diff -u -r2ce54f6e928b2c305f5240d3d5e5c9e348ca8749 -r037f0edb0b880130563058c809ba50308f2a63e9 --- firmware/App/Controllers/TemperatureSensors.c (.../TemperatureSensors.c) (revision 2ce54f6e928b2c305f5240d3d5e5c9e348ca8749) +++ firmware/App/Controllers/TemperatureSensors.c (.../TemperatureSensors.c) (revision 037f0edb0b880130563058c809ba50308f2a63e9) @@ -38,6 +38,7 @@ #define PRIMARY_HEATER_EXT_TEMP_SENSORS_0_DEGREE_RESISTANCE 1000U ///< Primary heater external temperature sensors zero degree resistance. #define COND_SENSORS_TEMP_SENSOR_GAIN 8U ///< Temperature sensor for conductivity gain. + #define COND_SENSORS_TEMP_SENSOR_REF_RESISTANCE 19600U ///< Temperature sensor for conductivity reference resistance. #define COND_SENSORS_TEMP_SENSOR_0_DEGREE_RESISTANCE 1000U ///< Temperature sensor for conductivity zero degree resistance. @@ -52,7 +53,7 @@ #define MAX_ALLOWED_TEMP_DELTA_BETWEEN_SENSORS 2U ///< Maximum allowed temperature delta between sensors. #define SHIFT_BITS_BY_2 2U ///< Shift bits by 2 to create a 4 for averaging 4 samples. #define SHIFT_BITS_BY_2_FOR_AVERAGING 2U ///< Shift the ADCs of the temperature sensors by 2 to average them. -#define INLET_WATER_TEMPERATURE_PERSISTENCE_PERIOD ( 5 * MS_PER_SECOND ) ///< Persistence period for temperature sensors out of range error period. +#define INLET_WATER_TEMPERATURE_PERSISTENCE_PERIOD ( 5 * MS_PER_SECOND ) ///< Persistence period for temperature sensors out of range error period. #define MIN_WATER_INPUT_TEMPERATURE 22U ///< Minimum water input temperature. #define MAX_WATER_INPUT_TEMPERATURE 35U ///< Maximum water input temperature. @@ -76,6 +77,7 @@ #define TEMPERATURE_SENSORS_FPGA_ERROR_PERSISTENT_PERIOD ( 5 * MS_PER_SECOND ) ///< Temperature sensors FPGA error persistent period. #define TEMPERATURE_SENSORS_INTERNAL_ERROR_PERSISTENT_PERIOD ( 3 * MS_PER_SECOND ) ///< Temperature sensors internal error persistent period. #define FPGA_RAW_ADC_READ_INTERVAL_COUNT 8 ///< Time interval in counts to read the raw ADC reads from FPGA. +#define TEMPERATURE_SENSORS_ERROR_FLAG_PERSISTENT_PERIOD ( 5 * MS_PER_SECOND ) ///< Temperature sensors error flag persistent period. /// Temperature sensor self-test states. typedef enum tempSensors_Self_Test_States @@ -252,7 +254,7 @@ initPersistentAlarm( ALARM_ID_INLET_WATER_HIGH_TEMPERATURE, INLET_WATER_TEMPERATURE_PERSISTENCE_PERIOD, INLET_WATER_TEMPERATURE_PERSISTENCE_PERIOD ); initPersistentAlarm( ALARM_ID_INLET_WATER_LOW_TEMPERATURE, INLET_WATER_TEMPERATURE_PERSISTENCE_PERIOD, INLET_WATER_TEMPERATURE_PERSISTENCE_PERIOD ); - // Persistent alarm for temperature sensors internal error + // Persistent alarm for temperature sensors ADC error // When the FPGA read count does not increment for a period of time, it is considered as an internal error of the temperature sensors // driver. This is internal because FPGA does not error out if the FPGA read count does not increment. initPersistentAlarm( ALARM_ID_DG_TEMPERATURE_SENSORS_ADC_FAULT, TEMPERATURE_SENSORS_FPGA_ERROR_PERSISTENT_PERIOD, TEMPERATURE_SENSORS_FPGA_ERROR_PERSISTENT_PERIOD ); @@ -362,7 +364,20 @@ } else { +#ifdef THD_USING_TRO_CONNECTOR + // In V3 THd is connected to TRo + // In V3 TDi represents TRo since they are very close to each other + if ( TEMPSENSORS_HEAT_DISINFECT == sensorIndex ) + { + temperature = tempSensors[ TEMPSENSORS_OUTLET_REDUNDANT ].temperatureValues.data; + } + else + { + temperature = tempSensors[ sensorIndex ].temperatureValues.data; + } +#else temperature = tempSensors[ sensorIndex ].temperatureValues.data; +#endif } } else @@ -493,8 +508,49 @@ { S32 convertedADC = (S32)( adc & MASK_OFF_U32_MSB ); - if ( TRUE == isADCReadValid( sensorIndex, fpgaError, fpgaCount ) ) + // All the sensors have ADC read and count values that have to be checked + BOOL isADCValid = isADCReadValid( sensorIndex, fpgaError, fpgaCount ); + + // Some of the temperature sensors have an MSB bit that is used as an + // error flag. This flag will be a TRUE by default. + BOOL isTemperatureNotValid = FALSE; + + switch( sensorIndex ) { + case TEMPSENSORS_LOAD_CELL_A1_B1: // 267 + case TEMPSENSORS_LOAD_CELL_A2_B2: // 279 + case TEMPSENSORS_CONDUCTIVITY_SENSOR_1: // 283 + case TEMPSENSORS_CONDUCTIVITY_SENSOR_2: // 287 + case TEMPSENSORS_OUTLET_PRIMARY_HEATER: // 291 + case TEMPSENSORS_INLET_PRIMARY_HEATER: // 295 + case TEMPSENSORS_INTERNAL_COND_TEMP_SENSOR: // 299 + case TEMPSENSORS_OUTLET_REDUNDANT: // 303 + case TEMPSENSORS_INTERNAL_THDO_RTD: // 307 + case TEMPSENSORS_INLET_DIALYSATE: // 311 + case TEMPSENSORS_INTERNAL_TDI_RTD: // 315 + { + // The MSB bit of the last byte is the error flag, so that MSB + // is shifted 31 bits to the first bit of the U32 variable. + // If that bit is a 1, there is either CRC error or Status error + // that are ored on top of each other + U32 errorBit = adc >> 31; + isTemperatureNotValid = errorBit > 0; + checkPersistentAlarm( ALARM_ID_DG_TEMPERATURE_SENSOR_FAULT, isTemperatureNotValid, sensorIndex, + TEMPERATURE_SENSORS_ERROR_FLAG_PERSISTENT_PERIOD ); + } + break; + + default: + // Do nothing. FPGA board temperature sensor does not have error flag bit + // If a wrong temperature sensor name is picked, the function that converts + // ADC counts to temperature raises an alarm. + break; + } + + // To update the moving average of a temperature sensor, both ADC and internal + // error flags must be valid + if ( ( TRUE == isADCValid ) && ( FALSE == isTemperatureNotValid ) ) + { processADCRead( sensorIndex, convertedADC ); } } @@ -557,7 +613,7 @@ } } - BOOL isThereAnError = !isFPGACountChanging || !isFPGAErrorZero; + BOOL isThereAnError = ( FALSE == isFPGACountChanging ) || ( FALSE == isFPGAErrorZero ); checkPersistentAlarm( ALARM_ID_DG_TEMPERATURE_SENSORS_ADC_FAULT, isThereAnError, sensorIndex, TEMPERATURE_SENSORS_FPGA_ERROR_PERSISTENT_PERIOD ); @@ -713,37 +769,62 @@ *************************************************************************/ static TEMPSENSORS_EXEC_STATES_T handleExecGetADCValues( void ) { + U32 rawADC = 0; + U32 errorCount = 0; + U32 readCount = 0; + // Look at the error counter and the specific error flag to make sure the error is a temperature sensor // Add a byte array to have bits for each sensor to find out exactly what sensor failed if ( ++fpgaRawADCReadInterval >= FPGA_RAW_ADC_READ_INTERVAL_COUNT ) { - processTempSnsrsADCRead( TEMPSENSORS_INLET_PRIMARY_HEATER, getFPGATPiTemp(), getFPGARTDErrorCount(), getFPGARTDReadCount() ); - processTempSnsrsADCRead( TEMPSENSORS_OUTLET_PRIMARY_HEATER, getFPGATPoTemp(), getFPGARTDErrorCount(), getFPGARTDReadCount() ); - processTempSnsrsADCRead( TEMPSENSORS_CONDUCTIVITY_SENSOR_1, getFPGACD1Temp(), getFPGARTDErrorCount(), getFPGARTDReadCount() ); - processTempSnsrsADCRead( TEMPSENSORS_CONDUCTIVITY_SENSOR_2, getFPGACD2Temp(), getFPGARTDErrorCount(), getFPGARTDReadCount() ); - processTempSnsrsADCRead( TEMPSENSORS_OUTLET_REDUNDANT, getFPGATHDoTemp(), getFPGATHDoErrorCount(), getFPGATHDoReadCount() ); - processTempSnsrsADCRead( TEMPSENSORS_INLET_DIALYSATE, getFPGATDiTemp(), getFPGATDiErrorCount(), getFPGATDiReadCount() ); + rawADC = getFPGATPiTemp(); + errorCount = (U32)getFPGARTDErrorCount(); + readCount = (U32)getFPGARTDReadCount(); + processTempSnsrsADCRead( TEMPSENSORS_INLET_PRIMARY_HEATER, rawADC, errorCount, readCount ); - processHtrsTempSnsrsADCRead( TEMPSENSORS_PRIMARY_HEATER_THERMO_COUPLE, getFPGAPrimaryHeaterTemp(), getFPGAPrimaryHeaterFlags(), - getFPGAPrimaryHeaterReadCount() ); + rawADC = getFPGATPoTemp(); + processTempSnsrsADCRead( TEMPSENSORS_OUTLET_PRIMARY_HEATER, rawADC, errorCount, readCount ); - processHtrsTempSnsrsADCRead( TEMPSENSORS_TRIMMER_HEATER_THERMO_COUPLE, getFPGATrimmerHeaterTemp(), getFPGATrimmerHeaterFlags(), - getFPGATrimmerHeaterReadCount() ); + rawADC = getFPGACD1Temp(); + processTempSnsrsADCRead( TEMPSENSORS_CONDUCTIVITY_SENSOR_1, rawADC, errorCount, readCount ); - processHtrsTempSnsrsADCRead( TEMPSENSORS_PRIMARY_HEATER_COLD_JUNCTION, getFPGAPrimaryColdJunctionTemp(), getFPGATrimmerHeaterFlags(), - getFPGAPrimaryHeaterReadCount() ); + rawADC = getFPGACD2Temp(); + processTempSnsrsADCRead( TEMPSENSORS_CONDUCTIVITY_SENSOR_2, rawADC, errorCount, readCount ); - processHtrsTempSnsrsADCRead( TEMPSENSORS_TRIMMER_HEATER_COLD_JUNCTION, getFPGATrimmerColdJunctionTemp(), getFPGATrimmerHeaterFlags(), - getFPGATrimmerHeaterReadCount() ); + rawADC = getFPGATRoTemp(); + errorCount = (U32)getFPGATRoErrorCount(); + readCount = (U32)getFPGATRoReadCount(); + processTempSnsrsADCRead( TEMPSENSORS_OUTLET_REDUNDANT, rawADC, errorCount, readCount ); + rawADC = getFPGATDiTemp(); + errorCount = (U32)getFPGATDiErrorCount(); + readCount = (U32)getFPGATDiReadCount(); + processTempSnsrsADCRead( TEMPSENSORS_INLET_DIALYSATE, rawADC, errorCount, readCount ); + + rawADC = getFPGAPrimaryHeaterTemp(); + errorCount = (U32)getFPGAPrimaryHeaterFlags(); + readCount = (U32)getFPGAPrimaryHeaterReadCount(); + processHtrsTempSnsrsADCRead( TEMPSENSORS_PRIMARY_HEATER_THERMO_COUPLE, rawADC, errorCount, readCount ); + + rawADC = getFPGAPrimaryColdJunctionTemp(); + processHtrsTempSnsrsADCRead( TEMPSENSORS_PRIMARY_HEATER_COLD_JUNCTION, rawADC, errorCount, readCount ); + + rawADC = getFPGATrimmerHeaterTemp(); + errorCount = (U32)getFPGATrimmerHeaterFlags(); + readCount = (U32)getFPGATrimmerHeaterReadCount(); + processHtrsTempSnsrsADCRead( TEMPSENSORS_TRIMMER_HEATER_THERMO_COUPLE, rawADC, errorCount, readCount ); + + rawADC = getFPGATrimmerColdJunctionTemp(); + processHtrsTempSnsrsADCRead( TEMPSENSORS_TRIMMER_HEATER_COLD_JUNCTION, rawADC, errorCount, readCount ); + // NOTE: FPGA board temperature sensor is different from the rest of the sensors. This sensor does not have FPGA count and error // coming from FPGA. It is kept here to do moving average on the values. The supporting functions need to see the FPGA read count // incrementing internally so there will not be any errors. U32 simulatedCounter = tempSensors[ TEMPSENSORS_FPGA_BOARD_SENSOR ].readCount; processTempSnsrsADCRead( TEMPSENSORS_FPGA_BOARD_SENSOR, getFPGABoardTemp(), 0, ++simulatedCounter ); processTempSnsrsADCRead( TEMPSENSORS_LOAD_CELL_A1_B1, getFPGALoadCellsA1B1Temp(), getFPGAADC1ErrorCount(), getFPGAADC1ReadCount() ); processTempSnsrsADCRead( TEMPSENSORS_LOAD_CELL_A2_B2, getFPGALoadCellsA2B2Temp(), getFPGAADC2ErrorCount(), getFPGAADC2ReadCount() ); - processTempSnsrsADCRead( TEMPSENSORS_INTERNAL_THDO_RTD, getFPGATHDoInternalTemp(), getFPGATHDoErrorCount(), getFPGATHDoReadCount() ); + processTempSnsrsADCRead( TEMPSENSORS_INTERNAL_THDO_RTD, getFPGATRoInternalTemp(), getFPGATRoErrorCount(), getFPGATRoReadCount() ); processTempSnsrsADCRead( TEMPSENSORS_INTERNAL_TDI_RTD, getFPGATDiInternalTemp(), getFPGATDiErrorCount(), getFPGATDiReadCount() ); processTempSnsrsADCRead( TEMPSENSORS_INTERNAL_COND_TEMP_SENSOR, getFPGACondSnsrInternalTemp(), getFPGARTDErrorCount(), getFPGARTDReadCount() ); @@ -795,28 +876,28 @@ { TEMPERATURE_SENSORS_DATA_T data; - data.inletPrimaryHeater = getTemperatureValue ( TEMPSENSORS_INLET_PRIMARY_HEATER ); - data.outletPrimaryHeater = getTemperatureValue ( TEMPSENSORS_OUTLET_PRIMARY_HEATER ); - data.conductivitySensor1 = getTemperatureValue ( TEMPSENSORS_CONDUCTIVITY_SENSOR_1 ); - data.conductivitySensor2 = getTemperatureValue ( TEMPSENSORS_CONDUCTIVITY_SENSOR_2 ); - data.outletRedundant = getTemperatureValue ( TEMPSENSORS_OUTLET_REDUNDANT ); - data.inletDialysate = getTemperatureValue ( TEMPSENSORS_INLET_DIALYSATE ); - data.primaryHeaterThermocouple = getTemperatureValue ( TEMPSENSORS_PRIMARY_HEATER_THERMO_COUPLE ); - data.trimmerHeaterThermocouple = getTemperatureValue ( TEMPSENSORS_TRIMMER_HEATER_THERMO_COUPLE ); - data.priamyHeaterColdjunction = getTemperatureValue ( TEMPSENSORS_PRIMARY_HEATER_COLD_JUNCTION ); - data.trimmerHeaterColdjunction = getTemperatureValue ( TEMPSENSORS_TRIMMER_HEATER_COLD_JUNCTION ); - data.primaryHeaterInternal = getTemperatureValue ( TEMPSENSORS_PRIMARY_HEATER_INTERNAL ); - data.trimmerHeaterInternal = getTemperatureValue ( TEMPSENSORS_TRIMMER_HEATER_INTERNAL ); - data.fpgaBoard = getTemperatureValue ( TEMPSENSORS_FPGA_BOARD_SENSOR ); - data.loadCellA1B1 = getTemperatureValue ( TEMPSENSORS_LOAD_CELL_A1_B1 ); - data.loadCellA2B2 = getTemperatureValue ( TEMPSENSORS_LOAD_CELL_A2_B2 ); - data.internalTHDORTD = getTemperatureValue ( TEMPSENSORS_INTERNAL_THDO_RTD ); - data.internalTDIRTD = getTemperatureValue ( TEMPSENSORS_INTERNAL_TDI_RTD ); - data.internalCondSnsrTemp = getTemperatureValue ( TEMPSENSORS_INTERNAL_COND_TEMP_SENSOR ); - data.primaryThermoCoupleRaw = tempSensors[ TEMPSENSORS_PRIMARY_HEATER_THERMO_COUPLE ].rawADCReads[ MAX_NUM_OF_RAW_ADC_SAMPLES - 1 ]; - data.primaryColdjuncRaw = tempSensors[ TEMPSENSORS_PRIMARY_HEATER_COLD_JUNCTION ].rawADCReads[ MAX_NUM_OF_RAW_ADC_SAMPLES - 1 ]; - data.trimmerThermoCoupleRaw = tempSensors[ TEMPSENSORS_TRIMMER_HEATER_THERMO_COUPLE ].rawADCReads[ MAX_NUM_OF_RAW_ADC_SAMPLES - 1 ]; - data.trimmerColdjuncRaw = tempSensors[ TEMPSENSORS_TRIMMER_HEATER_COLD_JUNCTION ].rawADCReads[ MAX_NUM_OF_RAW_ADC_SAMPLES - 1 ]; + data.inletPrimaryHeater = getTemperatureValue( TEMPSENSORS_INLET_PRIMARY_HEATER ); + data.outletPrimaryHeater = getTemperatureValue( TEMPSENSORS_OUTLET_PRIMARY_HEATER ); + data.conductivitySensor1 = getTemperatureValue( TEMPSENSORS_CONDUCTIVITY_SENSOR_1 ); + data.conductivitySensor2 = getTemperatureValue( TEMPSENSORS_CONDUCTIVITY_SENSOR_2 ); + data.outletRedundant = getTemperatureValue( TEMPSENSORS_OUTLET_REDUNDANT ); + data.inletDialysate = getTemperatureValue( TEMPSENSORS_INLET_DIALYSATE ); + data.primaryHeaterThermocouple = getTemperatureValue( TEMPSENSORS_PRIMARY_HEATER_THERMO_COUPLE ); + data.trimmerHeaterThermocouple = getTemperatureValue( TEMPSENSORS_TRIMMER_HEATER_THERMO_COUPLE ); + data.priamyHeaterColdjunction = getTemperatureValue( TEMPSENSORS_PRIMARY_HEATER_COLD_JUNCTION ); + data.trimmerHeaterColdjunction = getTemperatureValue( TEMPSENSORS_TRIMMER_HEATER_COLD_JUNCTION ); + data.primaryHeaterInternal = getTemperatureValue( TEMPSENSORS_PRIMARY_HEATER_INTERNAL ); + data.trimmerHeaterInternal = getTemperatureValue( TEMPSENSORS_TRIMMER_HEATER_INTERNAL ); + data.fpgaBoard = getTemperatureValue( TEMPSENSORS_FPGA_BOARD_SENSOR ); + data.loadCellA1B1 = getTemperatureValue( TEMPSENSORS_LOAD_CELL_A1_B1 ); + data.loadCellA2B2 = getTemperatureValue( TEMPSENSORS_LOAD_CELL_A2_B2 ); + data.internalTHDORTD = getTemperatureValue( TEMPSENSORS_INTERNAL_THDO_RTD ); + data.internalTDIRTD = getTemperatureValue( TEMPSENSORS_INTERNAL_TDI_RTD ); + data.internalCondSnsrTemp = getTemperatureValue( TEMPSENSORS_INTERNAL_COND_TEMP_SENSOR ); + data.primaryThermoCoupleRaw = getFPGAPrimaryHeaterTemp(); + data.primaryColdjuncRaw = getFPGAPrimaryColdJunctionTemp(); + data.trimmerThermoCoupleRaw = getFPGATrimmerHeaterTemp(); + data.trimmerColdjuncRaw = getFPGATrimmerColdJunctionTemp(); data.cond1Raw = tempSensors[ TEMPSENSORS_CONDUCTIVITY_SENSOR_1 ].rawADCReads[ MAX_NUM_OF_RAW_ADC_SAMPLES - 1 ]; data.cond2Raw = tempSensors[ TEMPSENSORS_CONDUCTIVITY_SENSOR_2 ].rawADCReads[ MAX_NUM_OF_RAW_ADC_SAMPLES - 1 ];