diff --git a/conf/modules/temp_adc.xml b/conf/modules/temp_adc.xml index 46fd8794fc..42e4914d17 100644 --- a/conf/modules/temp_adc.xml +++ b/conf/modules/temp_adc.xml @@ -5,11 +5,18 @@ Temperature ADC Measure temperature of 3 sensores connecter to any ADC - Can read LM35 or 10k / 100k NTC sensor + Can read LM35 or NTC sensor + + + + + + +
diff --git a/sw/airborne/mcu_periph/adc.h b/sw/airborne/mcu_periph/adc.h index 5ac865ab13..ee6cd692a9 100644 --- a/sw/airborne/mcu_periph/adc.h +++ b/sw/airborne/mcu_periph/adc.h @@ -45,6 +45,15 @@ microcontroller architecture. */ +/* Set the correct ADC resolution */ +#ifndef ADC_RESOLUTION +#if defined(STM32F1) || defined(STM32F4) +#define ADC_RESOLUTION 4096 +#else +#define ADC_RESOLUTION 1024 +#endif +#endif + /** Struct to collect samples from ADC and building an average over MAX_AV_NB_SAMPLE values. diff --git a/sw/airborne/modules/sensors/temp_adc.c b/sw/airborne/modules/sensors/temp_adc.c index 4b477d5160..a2312bd11b 100644 --- a/sw/airborne/modules/sensors/temp_adc.c +++ b/sw/airborne/modules/sensors/temp_adc.c @@ -31,7 +31,8 @@ #include "subsystems/datalink/downlink.h" #include BOARD_CONFIG -float temp_c1, temp_c2, temp_c3; +bool temp_adc_sync_send = false; +static float temp_c1, temp_c2, temp_c3; #if PERIODIC_TELEMETRY #include "subsystems/datalink/telemetry.h" @@ -48,26 +49,28 @@ float temp_c1, temp_c2, temp_c3; #endif #endif +#ifdef TEMP_ADC_CHANNEL1 +static struct adc_buf temp_buf1; + #ifndef TEMP_ADC_CHANNEL1_TYPE #define TEMP_ADC_CHANNEL1_TYPE LM35 #endif -#ifndef TEMP_ADC_CHANNEL2_TYPE -#define TEMP_ADC_CHANNEL2_TYPE LM35 -#endif -#ifndef TEMP_ADC_CHANNEL3_TYPE -#define TEMP_ADC_CHANNEL3_TYPE LM35 -#endif - -#ifdef TEMP_ADC_CHANNEL1 -static struct adc_buf temp_buf1; #endif #ifdef TEMP_ADC_CHANNEL2 static struct adc_buf temp_buf2; + +#ifndef TEMP_ADC_CHANNEL2_TYPE +#define TEMP_ADC_CHANNEL2_TYPE LM35 +#endif #endif #ifdef TEMP_ADC_CHANNEL3 static struct adc_buf temp_buf3; + +#ifndef TEMP_ADC_CHANNEL3_TYPE +#define TEMP_ADC_CHANNEL3_TYPE LM35 +#endif #endif #ifndef TEMP_ADC_NB_SAMPLES @@ -81,19 +84,22 @@ static struct adc_buf temp_buf3; #define TEMP_ADC_SYNC_SEND FALSE #endif -float calc_ntc(int16_t raw_temp) +/** + * Calculate the NTC tempreature in celcius based on the Steinhart equation + */ +static inline float calc_ntc(int16_t raw_adc, uint16_t pull_up_r, float a, float b, float c) { - float temp_c; - //calc for NTC - temp_c = log(((10240000 / raw_temp) - 10000) * 10); - //temp_c = 1/(0.001129148+(0.000234125*temp_c)+(0.0000000876741*temp_c*temp_c*temp_c)); - temp_c = 1 / (0.000603985662844 + (0.000229995493730 * temp_c) + (0.000000067653027 * temp_c * - temp_c * temp_c)); - temp_c = temp_c - 273.15; //convert do celcius + // Calculate the logaritmic resistance value based on the Pull up resistor + float log_r = log((pull_up_r * raw_adc) / (ADC_RESOLUTION - raw_adc)); + + // Steinhart equation (https://en.wikipedia.org/wiki/Steinhart%E2%80%93Hart_equation) + // 1 / T = a + b*len(R) + c*ln(R)³ + float temp_c = 1 / (a + (b * log_r) + (c * log_r * log_r * log_r)); + temp_c = temp_c - 273.15; // Convert do celcius return temp_c; } -float calc_lm35(int16_t raw_temp) +static inline float calc_lm35(int16_t raw_temp) { return ((float)raw_temp * (3300.0f / 1024.0f) / 10.0f); } @@ -103,6 +109,9 @@ static void temp_adc_downlink(struct transport_tx *trans, struct link_device *de pprz_msg_send_TEMP_ADC(trans, dev, AC_ID, &temp_c1, &temp_c2, &temp_c3); } +/** + * Temperature ADC initialize channels + */ void temp_adc_init(void) { temp_adc_sync_send = TEMP_ADC_SYNC_SEND; @@ -134,7 +143,8 @@ void temp_adc_periodic(void) #if TEMP_ADC_CHANNEL1_TYPE == LM35 temp_c1 = calc_lm35(adc_raw); #elif TEMP_ADC_CHANNEL1_TYPE == NTC - temp_c1 = calc_ntc(adc_raw); + temp_c1 = calc_ntc(adc_raw, TEMP_ADC_CHANNEL1_PU_R, + TEMP_ADC_CHANNEL1_A, TEMP_ADC_CHANNEL1_B, TEMP_ADC_CHANNEL1_C); #endif #endif @@ -143,7 +153,8 @@ void temp_adc_periodic(void) #if TEMP_ADC_CHANNEL2_TYPE == LM35 temp_c2 = calc_lm35(adc_raw); #elif TEMP_ADC_CHANNEL2_TYPE == NTC - temp_c2 = calc_ntc(adc_raw); + temp_c2 = calc_ntc(adc_raw, TEMP_ADC_CHANNEL2_PU_R, + TEMP_ADC_CHANNEL2_A, TEMP_ADC_CHANNEL2_B, TEMP_ADC_CHANNEL2_C); #endif #endif @@ -152,12 +163,13 @@ void temp_adc_periodic(void) #if TEMP_ADC_CHANNEL3_TYPE == LM35 temp_c3 = calc_lm35(adc_raw); #elif TEMP_ADC_CHANNEL3_TYPE == NTC - temp_c3 = calc_ntc(adc_raw); + temp_c3 = calc_ntc(adc_raw, TEMP_ADC_CHANNEL3_PU_R, + TEMP_ADC_CHANNEL3_A, TEMP_ADC_CHANNEL3_B, TEMP_ADC_CHANNEL3_C); #endif #endif + /* Send measurements as soon as they are calculated */ if (temp_adc_sync_send) { temp_adc_downlink(&(DefaultChannel).trans_tx, &(DefaultDevice).device); } - } diff --git a/sw/airborne/modules/sensors/temp_adc.h b/sw/airborne/modules/sensors/temp_adc.h index 64da048e49..ab6abc7550 100644 --- a/sw/airborne/modules/sensors/temp_adc.h +++ b/sw/airborne/modules/sensors/temp_adc.h @@ -28,12 +28,7 @@ #include "std.h" -/// flag to enable sending every new measurement via telemetry -bool temp_adc_sync_send; - -float calc_ntc(int16_t raw_temp); -float calc_lm35(int16_t raw_temp); - +extern bool temp_adc_sync_send; void temp_adc_init(void); void temp_adc_periodic(void);