6565 defined(STM32F437xx ) || defined(STM32F439xx ) || \
6666 defined(STM32F746xx )
6767#define VBAT_DIV (4)
68+ #elif defined(STM32L476xx )
69+ #define VBAT_DIV (3)
6870#else
6971#error Unsupported processor
7072#endif
@@ -80,8 +82,45 @@ typedef struct _pyb_obj_adc_t {
8082 ADC_HandleTypeDef handle ;
8183} pyb_obj_adc_t ;
8284
85+ STATIC bool is_adcx_channel (int channel ) {
86+ #if defined(MCU_SERIES_F4 ) || defined(MCU_SERIES_F7 )
87+ return IS_ADC_CHANNEL (channel );
88+ #elif defined(MCU_SERIES_L4 )
89+ ADC_HandleTypeDef handle ;
90+ handle .Instance = ADCx ;
91+ return IS_ADC_CHANNEL (& handle , channel );
92+ #else
93+ #error Unsupported processor
94+ #endif
95+ }
96+
97+ STATIC void adc_wait_for_eoc_or_timeout (int32_t timeout ) {
98+ uint32_t tickstart = HAL_GetTick ();
99+ #if defined(MCU_SERIES_F4 ) || defined(MCU_SERIES_F7 )
100+ while ((ADCx -> SR & ADC_FLAG_EOC ) != ADC_FLAG_EOC ) {
101+ #elif defined(MCU_SERIES_L4)
102+ while (READ_BIT (ADCx -> ISR , ADC_FLAG_EOC ) != ADC_FLAG_EOC ) {
103+ #else
104+ #error Unsupported processor
105+ #endif
106+ if (((HAL_GetTick () - tickstart ) > timeout )) {
107+ break ; // timeout
108+ }
109+ }
110+ }
111+
112+ STATIC void adcx_clock_enable (void ) {
113+ #if defined(MCU_SERIES_F4 ) || defined(MCU_SERIES_F7 )
114+ ADCx_CLK_ENABLE ();
115+ #elif defined(MCU_SERIES_L4 )
116+ __HAL_RCC_ADC_CLK_ENABLE ();
117+ #else
118+ #error Unsupported processor
119+ #endif
120+ }
121+
83122STATIC void adc_init_single (pyb_obj_adc_t * adc_obj ) {
84- if (!IS_ADC_CHANNEL (adc_obj -> channel )) {
123+ if (!is_adcx_channel (adc_obj -> channel )) {
85124 return ;
86125 }
87126
@@ -97,22 +136,33 @@ STATIC void adc_init_single(pyb_obj_adc_t *adc_obj) {
97136 HAL_GPIO_Init (pin -> gpio , & GPIO_InitStructure );
98137 }
99138
100- ADCx_CLK_ENABLE ();
139+ adcx_clock_enable ();
101140
102141 ADC_HandleTypeDef * adcHandle = & adc_obj -> handle ;
103142 adcHandle -> Instance = ADCx ;
104- adcHandle -> Init .ClockPrescaler = ADC_CLOCKPRESCALER_PCLK_DIV2 ;
105143 adcHandle -> Init .Resolution = ADC_RESOLUTION12b ;
106- adcHandle -> Init .ScanConvMode = DISABLE ;
107144 adcHandle -> Init .ContinuousConvMode = DISABLE ;
108145 adcHandle -> Init .DiscontinuousConvMode = DISABLE ;
109146 adcHandle -> Init .NbrOfDiscConversion = 0 ;
110147 adcHandle -> Init .ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE ;
111- adcHandle -> Init .ExternalTrigConv = ADC_EXTERNALTRIGCONV_T1_CC1 ;
112148 adcHandle -> Init .DataAlign = ADC_DATAALIGN_RIGHT ;
113149 adcHandle -> Init .NbrOfConversion = 1 ;
114150 adcHandle -> Init .DMAContinuousRequests = DISABLE ;
115151 adcHandle -> Init .EOCSelection = DISABLE ;
152+ #if defined(MCU_SERIES_F4 ) || defined(MCU_SERIES_F7 )
153+ adcHandle -> Init .ClockPrescaler = ADC_CLOCKPRESCALER_PCLK_DIV2 ;
154+ adcHandle -> Init .ScanConvMode = DISABLE ;
155+ adcHandle -> Init .ExternalTrigConv = ADC_EXTERNALTRIGCONV_T1_CC1 ;
156+ #elif defined(MCU_SERIES_L4 )
157+ adcHandle -> Init .ClockPrescaler = ADC_CLOCK_ASYNC_DIV2 ;
158+ adcHandle -> Init .ScanConvMode = ADC_SCAN_DISABLE ;
159+ adcHandle -> Init .ExternalTrigConv = ADC_EXTERNALTRIG_T1_CC1 ;
160+ adcHandle -> Init .LowPowerAutoWait = DISABLE ;
161+ adcHandle -> Init .Overrun = ADC_OVR_DATA_PRESERVED ;
162+ adcHandle -> Init .OversamplingMode = DISABLE ;
163+ #else
164+ #error Unsupported processor
165+ #endif
116166
117167 HAL_ADC_Init (adcHandle );
118168}
@@ -122,7 +172,13 @@ STATIC void adc_config_channel(pyb_obj_adc_t *adc_obj) {
122172
123173 sConfig .Channel = adc_obj -> channel ;
124174 sConfig .Rank = 1 ;
175+ #if defined(MCU_SERIES_F4 ) || defined(MCU_SERIES_F7 )
125176 sConfig .SamplingTime = ADC_SAMPLETIME_15CYCLES ;
177+ #elif defined(MCU_SERIES_L4 )
178+ sConfig .SamplingTime = ADC_SAMPLETIME_12CYCLES_5 ;
179+ #else
180+ #error Unsupported processor
181+ #endif
126182 sConfig .Offset = 0 ;
127183
128184 HAL_ADC_ConfigChannel (& adc_obj -> handle , & sConfig );
@@ -173,7 +229,7 @@ STATIC mp_obj_t adc_make_new(const mp_obj_type_t *type, mp_uint_t n_args, mp_uin
173229 channel = pin -> adc_channel ;
174230 }
175231
176- if (!IS_ADC_CHANNEL (channel )) {
232+ if (!is_adcx_channel (channel )) {
177233 nlr_raise (mp_obj_new_exception_msg_varg (& mp_type_ValueError , "not a valid ADC Channel: %d" , channel ));
178234 }
179235 if (pin_adc1 [channel ] == NULL ) {
@@ -274,17 +330,18 @@ STATIC mp_obj_t adc_read_timed(mp_obj_t self_in, mp_obj_t buf_in, mp_obj_t freq_
274330 HAL_ADC_Start (& self -> handle );
275331 } else {
276332 // for subsequent samples we can just set the "start sample" bit
333+ #if defined(MCU_SERIES_F4 ) || defined(MCU_SERIES_F7 )
277334 ADCx -> CR2 |= (uint32_t )ADC_CR2_SWSTART ;
335+ #elif defined(MCU_SERIES_L4 )
336+ SET_BIT (ADCx -> CR , ADC_CR_ADSTART );
337+ #else
338+ #error Unsupported processor
339+ #endif
278340 }
279341
280342 // wait for sample to complete
281- uint32_t tickstart = HAL_GetTick ();
282- while ((ADCx -> SR & ADC_FLAG_EOC ) != ADC_FLAG_EOC ) {
283- #define READ_TIMED_TIMEOUT (10) // in ms
284- if (((HAL_GetTick () - tickstart ) > READ_TIMED_TIMEOUT )) {
285- break ; // timeout
286- }
287- }
343+ #define READ_TIMED_TIMEOUT (10) // in ms
344+ adc_wait_for_eoc_or_timeout (READ_TIMED_TIMEOUT );
288345
289346 // read value
290347 uint value = ADCx -> DR ;
@@ -357,22 +414,33 @@ void adc_init_all(pyb_adc_all_obj_t *adc_all, uint32_t resolution) {
357414 HAL_GPIO_Init (pin -> gpio , & GPIO_InitStructure );
358415 }
359416
360- ADCx_CLK_ENABLE ();
417+ adcx_clock_enable ();
361418
362419 ADC_HandleTypeDef * adcHandle = & adc_all -> handle ;
363420 adcHandle -> Instance = ADCx ;
364- adcHandle -> Init .ClockPrescaler = ADC_CLOCKPRESCALER_PCLK_DIV2 ;
365421 adcHandle -> Init .Resolution = resolution ;
366- adcHandle -> Init .ScanConvMode = DISABLE ;
367422 adcHandle -> Init .ContinuousConvMode = DISABLE ;
368423 adcHandle -> Init .DiscontinuousConvMode = DISABLE ;
369424 adcHandle -> Init .NbrOfDiscConversion = 0 ;
370425 adcHandle -> Init .ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE ;
371- adcHandle -> Init .ExternalTrigConv = ADC_EXTERNALTRIGCONV_T1_CC1 ;
372426 adcHandle -> Init .DataAlign = ADC_DATAALIGN_RIGHT ;
373427 adcHandle -> Init .NbrOfConversion = 1 ;
374428 adcHandle -> Init .DMAContinuousRequests = DISABLE ;
375429 adcHandle -> Init .EOCSelection = DISABLE ;
430+ #if defined(MCU_SERIES_F4 ) || defined(MCU_SERIES_F7 )
431+ adcHandle -> Init .ClockPrescaler = ADC_CLOCKPRESCALER_PCLK_DIV2 ;
432+ adcHandle -> Init .ScanConvMode = DISABLE ;
433+ adcHandle -> Init .ExternalTrigConv = ADC_EXTERNALTRIGCONV_T1_CC1 ;
434+ #elif defined(MCU_SERIES_L4 )
435+ adcHandle -> Init .ClockPrescaler = ADC_CLOCK_ASYNC_DIV2 ;
436+ adcHandle -> Init .ScanConvMode = ADC_SCAN_DISABLE ;
437+ adcHandle -> Init .ExternalTrigConv = ADC_EXTERNALTRIG_T1_CC1 ;
438+ adcHandle -> Init .LowPowerAutoWait = DISABLE ;
439+ adcHandle -> Init .Overrun = ADC_OVR_DATA_PRESERVED ;
440+ adcHandle -> Init .OversamplingMode = DISABLE ;
441+ #else
442+ #error Unsupported processor
443+ #endif
376444
377445 HAL_ADC_Init (adcHandle );
378446}
@@ -381,7 +449,13 @@ uint32_t adc_config_and_read_channel(ADC_HandleTypeDef *adcHandle, uint32_t chan
381449 ADC_ChannelConfTypeDef sConfig ;
382450 sConfig .Channel = channel ;
383451 sConfig .Rank = 1 ;
452+ #if defined(MCU_SERIES_F4 ) || defined(MCU_SERIES_F7 )
384453 sConfig .SamplingTime = ADC_SAMPLETIME_15CYCLES ;
454+ #elif defined(MCU_SERIES_L4 )
455+ sConfig .SamplingTime = ADC_SAMPLETIME_12CYCLES_5 ;
456+ #else
457+ #error Unsupported processor
458+ #endif
385459 sConfig .Offset = 0 ;
386460 HAL_ADC_ConfigChannel (adcHandle , & sConfig );
387461
0 commit comments