/** * @brief get STM32g0x0 CPU temperature using fixpoint * @param[in] * @param[out] none * @retval temperature in 1/10°Celsius * @Author Klaus Mezger */ uint16_t ecGetCPUTemp(uint16_t ADCvalue) { /* Tested with STM32G070 and g030. * This routine is fast because of using fixoint arithmetic. * Works without TS_CAL2, because this is not mentioned in the datasheets of STM32G030 and g070. * Even with using TS_CAL2 from STM32g031 / g071 you do possibly not get better results * */ /* 130° and 30°C values from STM32G031 / STM32G071 */ #define TEMP30_CAL *(uint16_t*) 0x1FFF75A8 #define TEMP130_CAL *(uint16_t*) 0x1FFF75CA //Not existent in STM32G0x0 DS, used here as test reference #define REF_TEMP 30 //calibration from datasheet /* decimal fixpoint d.1 */ #define SLOPE_Y 25 //10*mV /°C from datasheet #define SLOPE_Y_INV (int32_t)(100000/SLOPE_Y) //10 * inverse of slope #define VDDA_10d1 33 //VDDA 3.3V #define VREF_CAL_10d1 30 //VDDA 3.0V reference used in factory TS_CALx values uint32_t cal30; int16_t temp_10d1; //resulting temperature int32_t adc_0; /* calc 30°C reference using VDDA 3.3V */ cal30 = (TEMP30_CAL * VREF_CAL_10d1 / VDDA_10d1); //ADC at 30° @ VDDA = 3.3V /* calc ADC value @ 0°C using typical TS slope from datasheet */ adc_0 = cal30 - ((REF_TEMP * SLOPE_Y << 12) / VDDA_10d1) / 1000; //calculate offset @ 0°C /* calculate temperature based on TS offset @ 0°C */ temp_10d1 = (ADCvalue - adc_0) * ((SLOPE_Y_INV * VDDA_10d1) >> 12) / 10; // skip last digit // original formula needs float temp = ((130-30)/(TS_CAL2 - TS_CAL1)) * (TS_DATA * TS_CAL1) + 30 return temp_10d1; }