|
| 1 | +/* |
| 2 | + Internal_channels |
| 3 | + This example shows how to read then convert to proper Unit the 3 internal channels + A0. |
| 4 | +
|
| 5 | + analogRead() can now be used to read some internal channels with the following definitions: |
| 6 | + ATEMP: internal temperature sensor |
| 7 | + AVREF: VrefInt, internal voltage reference |
| 8 | + AVBAT: Vbat voltage |
| 9 | +
|
| 10 | + A minimum ADC sampling time is required when reading internal channels |
| 11 | + so default is set it to max possible value. |
| 12 | + It can be defined more precisely by defining: |
| 13 | + ADC_SAMPLINGTIME_INTERNAL to the desired ADC sample time. |
| 14 | +
|
| 15 | + ADC_SAMPLINGTIME and ADC_CLOCK_DIV could also be redefined by the variant or using build_opt.h. |
| 16 | +
|
| 17 | + This example is provided "as it" and can require some update mainly for datasheet values. |
| 18 | +*/ |
| 19 | + |
| 20 | +#include "stm32yyxx_ll_adc.h" |
| 21 | + |
| 22 | +/* Values available in datasheet */ |
| 23 | +#define CALX_TEMP 25 |
| 24 | +#if defined(STM32F1xx) |
| 25 | +#define V25 1430 |
| 26 | +#define AVG_SLOPE 4300 |
| 27 | +#define VREFINT 1200 |
| 28 | +#elif defined(STM32F2xx) || defined(STM32F4xx) |
| 29 | +#define V25 760 |
| 30 | +#define AVG_SLOPE 2500 |
| 31 | +#define VREFINT 1210 |
| 32 | +#endif |
| 33 | + |
| 34 | +/* Analog read resolution */ |
| 35 | +#define LL_ADC_RESOLUTION LL_ADC_RESOLUTION_12B |
| 36 | +#define ADC_RANGE 4096 |
| 37 | + |
| 38 | +// the setup routine runs once when you press reset: |
| 39 | +void setup() { |
| 40 | + // initialize serial communication at 9600 bits per second: |
| 41 | + Serial.begin(9600); |
| 42 | + while (!Serial); |
| 43 | + analogReadResolution(12); |
| 44 | +} |
| 45 | + |
| 46 | +static int32_t readVref() |
| 47 | +{ |
| 48 | +#ifdef __LL_ADC_CALC_VREFANALOG_VOLTAGE |
| 49 | +#ifdef STM32U5xx |
| 50 | + return (__LL_ADC_CALC_VREFANALOG_VOLTAGE(ADC1, analogRead(AVREF), LL_ADC_RESOLUTION)); |
| 51 | +#else |
| 52 | + return (__LL_ADC_CALC_VREFANALOG_VOLTAGE(analogRead(AVREF), LL_ADC_RESOLUTION)); |
| 53 | +#endif |
| 54 | +#else |
| 55 | + return (VREFINT * ADC_RANGE / analogRead(AVREF)); // ADC sample to mV |
| 56 | +#endif |
| 57 | +} |
| 58 | + |
| 59 | +#ifdef ATEMP |
| 60 | +static int32_t readTempSensor(int32_t VRef) |
| 61 | +{ |
| 62 | +#ifdef __LL_ADC_CALC_TEMPERATURE |
| 63 | +#ifdef STM32U5xx |
| 64 | + return (__LL_ADC_CALC_TEMPERATURE(ADC1, VRef, analogRead(ATEMP), LL_ADC_RESOLUTION)); |
| 65 | +#else |
| 66 | + return (__LL_ADC_CALC_TEMPERATURE(VRef, analogRead(ATEMP), LL_ADC_RESOLUTION)); |
| 67 | +#endif |
| 68 | +#elif defined(__LL_ADC_CALC_TEMPERATURE_TYP_PARAMS) |
| 69 | + return (__LL_ADC_CALC_TEMPERATURE_TYP_PARAMS(AVG_SLOPE, V25, CALX_TEMP, VRef, analogRead(ATEMP), LL_ADC_RESOLUTION)); |
| 70 | +#else |
| 71 | + return 0; |
| 72 | +#endif |
| 73 | +} |
| 74 | +#endif |
| 75 | + |
| 76 | +static int32_t readVoltage(int32_t VRef, uint32_t pin) |
| 77 | +{ |
| 78 | +#ifdef STM32U5xx |
| 79 | + return (__LL_ADC_CALC_DATA_TO_VOLTAGE(ADC1, VRef, analogRead(pin), LL_ADC_RESOLUTION)); |
| 80 | +#else |
| 81 | + return (__LL_ADC_CALC_DATA_TO_VOLTAGE(VRef, analogRead(pin), LL_ADC_RESOLUTION)); |
| 82 | +#endif |
| 83 | +} |
| 84 | + |
| 85 | +// The loop routine runs over and over again forever: |
| 86 | +void loop() { |
| 87 | + // Print out the value read |
| 88 | + int32_t VRef = readVref(); |
| 89 | + Serial.printf("VRef(mv)= %i", VRef); |
| 90 | +#ifdef ATEMP |
| 91 | + Serial.printf("\tTemp(°C)= %i", readTempSensor(VRef)); |
| 92 | +#endif |
| 93 | +#ifdef AVBAT |
| 94 | + Serial.printf("\tVbat(mv)= %i", readVoltage(VRef, AVBAT)); |
| 95 | +#endif |
| 96 | + Serial.printf("\tA0(mv)= %i\n", readVoltage(VRef, A0)); |
| 97 | + delay(200); |
| 98 | +} |
0 commit comments