Skip to content

Commit 997a168

Browse files
committed
cpu/stm32{f3,l4,wb,wl}: increase sampling time for VBat line
1 parent a418b49 commit 997a168

File tree

3 files changed

+47
-13
lines changed

3 files changed

+47
-13
lines changed

cpu/stm32/periph/adc_f3.c

Lines changed: 23 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,18 @@
2626
#include "periph_conf.h"
2727
#include "periph/vbat.h"
2828

29-
#define SMP_MIN (0x2) /*< Sampling time for slow channels
30-
(0x2 = 4.5 ADC clock cycles) */
29+
#define ADC_SMP_MIN_VAL (0x2) /*< Sampling time for slow channels
30+
(0x2 = 4.5 ADC clock cycles) */
31+
#define ADC_SMP_VBAT_VAL (0x5) /*< Sampling time when the VBat channel
32+
is read (0x5 = 61.5 ADC clock cycles) */
33+
34+
/* The sampling time width is 3 bit */
35+
#define ADC_SMP_BIT_WIDTH (3)
36+
37+
/* The sampling time can be specified for each channel over SMPR1 and SMPR2.
38+
This specifies the first channel that goes to SMPR2 instead of SMPR1. */
39+
#define ADC_SMPR2_FIRST_CHAN (10)
40+
3141
#ifdef ADC1_COMMON
3242
#define ADC_INSTANCE ADC1_COMMON
3343
#else
@@ -169,12 +179,21 @@ int adc_init(adc_t line)
169179
dev(line)->SQR1 |= (0 & ADC_SQR1_L);
170180
}
171181

182+
/* determine the right sampling time */
183+
uint32_t smp_time = ADC_SMP_MIN_VAL;
184+
if (IS_USED(MODULE_PERIPH_VBAT) && line == VBAT_ADC) {
185+
smp_time = ADC_SMP_VBAT_VAL;
186+
}
187+
172188
/* Configure sampling time for the given channel */
173189
if (adc_config[line].chan < 10) {
174-
dev(line)->SMPR1 = (SMP_MIN << (adc_config[line].chan * 3));
190+
dev(line)->SMPR1 = (smp_time << (adc_config[line].chan
191+
* ADC_SMP_BIT_WIDTH));
175192
}
176193
else {
177-
dev(line)->SMPR2 = (SMP_MIN << ((adc_config[line].chan - 10) * 3));
194+
dev(line)->SMPR2 = (smp_time << ((adc_config[line].chan
195+
- ADC_SMPR2_FIRST_CHAN)
196+
* ADC_SMP_BIT_WIDTH));
178197
}
179198

180199
/* Power off and unlock device again */

cpu/stm32/periph/adc_l4_wb.c

Lines changed: 16 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -54,8 +54,11 @@
5454
works on all channels.
5555
TCONV = Sampling time + 12.5 ADC clock cycles (RM section 18.4.12)
5656
At 80MHz this means we need to set SMP to 001 (6.5 ADC clock cycles) to
57-
stay within specs. (80000000/(6.5+12.5)) = 4210526 */
58-
#define ADC_SMP_MIN_VAL (0x1)
57+
stay within specs. (80000000/(6.5+12.5)) = 4210526. */
58+
#define ADC_SMP_MIN_VAL (0x2)
59+
/* Reading the battery voltage V_BAT is much slower and requires 92.5
60+
ADC clock cycles. */
61+
#define ADC_SMP_VBAT_VAL (0x5)
5962

6063
/* The sampling time width is 3 bit */
6164
#define ADC_SMP_BIT_WIDTH (3)
@@ -191,15 +194,21 @@ int adc_init(adc_t line)
191194
dev(line)->SQR1 &= ~ADC_SQR1_L_Msk;
192195
}
193196

197+
/* determine the right sampling time */
198+
uint32_t smp_time = ADC_SMP_MIN_VAL;
199+
if (IS_USED(MODULE_PERIPH_VBAT) && line == VBAT_ADC) {
200+
smp_time = ADC_SMP_VBAT_VAL;
201+
}
202+
194203
/* configure sampling time for the given channel */
195204
if (adc_config[line].chan < ADC_SMPR2_FIRST_CHAN) {
196-
dev(line)->SMPR1 = (ADC_SMP_MIN_VAL << (adc_config[line].chan *
197-
ADC_SMP_BIT_WIDTH));
205+
dev(line)->SMPR1 = (smp_time << (adc_config[line].chan
206+
* ADC_SMP_BIT_WIDTH));
198207
}
199208
else {
200-
dev(line)->SMPR2 = (ADC_SMP_MIN_VAL << ((adc_config[line].chan -
201-
ADC_SMPR2_FIRST_CHAN)
202-
* ADC_SMP_BIT_WIDTH));
209+
dev(line)->SMPR2 = (smp_time << ((adc_config[line].chan
210+
- ADC_SMPR2_FIRST_CHAN)
211+
* ADC_SMP_BIT_WIDTH));
203212
}
204213

205214
/* free the device again */

cpu/stm32/periph/adc_wl.c

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -148,8 +148,14 @@ int adc_init(adc_t line)
148148
/* set sequence length to 1 conversion */
149149
ADC->CFGR1 &= ~ADC_CFGR1_CONT;
150150

151-
/* Sampling time of 39.5 ADC clocks for all channels*/
152-
ADC->SMPR = ADC_SMPR_SMP1_2 | ADC_SMPR_SMP1_0;
151+
/* Set Sampling Time Register 1 to 3.5 ADC Cycles for all GPIO-Channels
152+
* and Sampling Time Register 2 to 39.5 ADC Cycles for VBat. Set the
153+
* VBat channel to use Sampling Time Register 2. */
154+
ADC->SMPR = ADC_SMPR_SMP1_0;
155+
if (IS_USED(MODULE_PERIPH_VBAT)) {
156+
ADC->SMPR |= ADC_SMPR_SMP2_2 | ADC_SMPR_SMP2_0 |
157+
(1 << (adc_config[VBAT_ADC].chan+ ADC_SMPR_SMPSEL_Pos));
158+
}
153159
}
154160

155161
/* free the device again */

0 commit comments

Comments
 (0)