1

I am working on my first project using an STM32F103 microcontroller. I am trying to read the temperature and to print it out every second. The code seems to do its job sometimes but on a few occasions the function returns 0 when it clearly should not return 0.

I have defined the last_values to be fixed values so that the calculation should allways be a positive number.

The function where things seem to mess up:

float TempSensor::getTemp() {
    uint32_t average = 0;
    for (int index = 0; index < AVERAGE_SIZE; index++)
        average += last_values[index];


    float average_val = average / AVERAGE_SIZE;
    
    printf("Value %f, Address %p\n\r", average_val, (void*) &average_val);
    printf("Average: %lu/%d=%f\n\r", average, AVERAGE_SIZE, average_val);
    
    float result = 1 / (1 / (T0 + 273.15) + (log(((average_val * R1) / (ADC_RES - average_val)) / R0)) / B) - 273.15;
    return result < 0 ? -25.0 : result;
}

The tempp_sensor.h file:

#ifndef INC_JEMINA_TEMP_SENSOR_H_
#define INC_JEMINA_TEMP_SENSOR_H_

#include "Jemina/Jemina.h"
#include "math.h"

const uint8_t AVERAGE_SIZE = 5;

//extern ADC_HandleTypeDef hadc1;

class TempSensor {
private:
    uint8_t channel;
    uint32_t last_values[AVERAGE_SIZE] = { 1111 , 2222, 3333, 4444, 5555};

public:
    static uint32_t value[4];
    TempSensor(uint8_t channel);
    float getTemp();
    void readTemp();
    static void init();
};

#endif /* INC_JEMINA_TEMP_SENSOR_H_ */

The function call using an interrupt on timer 6

void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim) {
    if (htim == &htim6) { //Gets called once every second
        printf("H0 temp: %f\n\n\r", H0_TEMP.getTemp());
    }
}

Output:

Value 3333.000000, Address 0x2000bf68
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 0.000000, Address 0x40aa0a00
Average: 16665/5=0.000000
H0 temp: 0.000000

Value 0.000000, Address 0x40aa0a00
Average: 16665/5=0.000000
H0 temp: 0.000000

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 0.000000, Address 0x40aa0a00
Average: 16665/5=0.000000
H0 temp: 0.000000

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 0.000000, Address 0x40aa0a00
Average: 16665/5=0.000000
H0 temp: 0.000000

Value 0.000000, Address 0x40aa0a00
Average: 16665/5=0.000000
H0 temp: 0.000000

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 0.000000, Address 0x40aa0a00
Average: 16665/5=0.000000
H0 temp: 0.000000

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 0.000000, Address 0x40aa0a00
Average: 16665/5=0.000000
H0 temp: 0.000000

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 3333.000000, Address 0x2000bf88
Average: 16665/5=3333.000000
H0 temp: 65.428040

Value 0.000000, Address 0x40aa0a00
Average: 16665/5=0.000000
H0 temp: 0.000000

Value 0.000000, Address 0x40aa0a00
Average: 16665/5=0.000000
H0 temp: 0.000000

As you can see the average_val should allways be 16665/5=3333.0 but sometimes it remains 0.0. One thing I noticed is that the address is also different when the calculation seems to go wrong.

Does anyone know why this happens and how I can fix it?

  • 1
    Tell-tale signs of [demons flying out of everyone's nose](http://www.catb.org/jargon/html/N/nasal-demons.html) due to undefined behavior somewhere in your program. The bug can be anywhere, and I doubt that anyone will be able to tell you why, since it will be necessary to attempt to analyze and debug the entire program in order to isolate the bug. – Sam Varshavchik Jan 01 '21 at 22:27
  • 1
    The large difference between the stack addresses suggests multiple threads are involved, and so does the comment about interrupts. Don't know enough about the STM32 environment to guess whether calling `printf` from an interrupt handler is even legal, but in any case the question needs a lot more code and context than provided. – dxiv Jan 01 '21 at 22:50
  • 2
    ... or a lot less code. Do you get the same problem if you just read the sensor in a loop where you sleep 1 second between reading? – Ted Lyngmo Jan 01 '21 at 22:53
  • 2
    I removed the printf statements from the functions and added a global variable to store the value in stead of printing it in the interrupt handler. When I print the value in the loop everything seems to work properly. Guess that calling printf in an interrupt caused the problem then. Thank you for your replies! – Thijs Alberts Jan 02 '21 at 11:18
  • Just a note: Strangely, `0x40aa0a00` is not even a valid address for STM32F103. It's not in the SRAM area where the stack is allocated. `0x40000000` is the start of peripheral registers, but they don't seem to reach `0x40aa0a00`. – Tagli Jan 03 '21 at 13:00

0 Answers0