Page 1 of 1

PATCH: enable STM32/LLD/ADCv2 analog watchdog  Topic is solved

Posted: Fri Nov 24, 2017 3:02 pm
by Thargon
Hi,
below a patch that enables the analog watchdog functionality for the STM32 ADCv2 low-level driver. Be aware that the memory footprint of the ADCDriver struct increases by four bytes. I have not introduced any macro switches to enable/disable the analog watchdog functionality, so this reduces code efficiency in case you do not need the feature.

Code: Select all

From d5e13e540dec58ece6de3d246a166185418f3fd3 Mon Sep 17 00:00:00 2001
Date: Mon, 12 Jun 2017 17:27:13 +0200
Subject: [PATCH] Introduced support for the ADC analog watchdog (ADCv2 only).

---
 os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.c | 20 +++++++++++++++++---
 os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.h | 21 ++++++++++++++++++++-
 2 files changed, 37 insertions(+), 4 deletions(-)

diff --git a/os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.c b/os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.c
index b2e651e..d5875ee 100644
--- a/os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.c
+++ b/os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.c
@@ -124,7 +124,11 @@ OSAL_IRQ_HANDLER(STM32_ADC_HANDLER) {
     if (ADCD1.grpp != NULL)
       _adc_isr_error_code(&ADCD1, ADC_ERR_OVERFLOW);
   }
-  /* TODO: Add here analog watchdog handling.*/
+  if (sr & ADC_SR_AWD) {
+    if (ADCD1.grpp != NULL) {
+      _adc_isr_error_code(&ADCD1, ADC_ERR_WATCHDOG);
+    }
+  }
 #if defined(STM32_ADC_ADC1_IRQ_HOOK)
   STM32_ADC_ADC1_IRQ_HOOK
 #endif
@@ -141,7 +145,11 @@ OSAL_IRQ_HANDLER(STM32_ADC_HANDLER) {
     if (ADCD2.grpp != NULL)
       _adc_isr_error_code(&ADCD2, ADC_ERR_OVERFLOW);
   }
-  /* TODO: Add here analog watchdog handling.*/
+  if (sr & ADC_SR_AWD) {
+    if (ADCD2.grpp != NULL) {
+      _adc_isr_error_code(&ADCD2, ADC_ERR_WATCHDOG);
+    }
+  }
 #if defined(STM32_ADC_ADC2_IRQ_HOOK)
   STM32_ADC_ADC2_IRQ_HOOK
 #endif
@@ -158,7 +166,11 @@ OSAL_IRQ_HANDLER(STM32_ADC_HANDLER) {
     if (ADCD3.grpp != NULL)
       _adc_isr_error_code(&ADCD3, ADC_ERR_OVERFLOW);
   }
-  /* TODO: Add here analog watchdog handling.*/
+  if (sr & ADC_SR_AWD) {
+    if (ADCD3.grpp != NULL) {
+      _adc_isr_error_code(&ADCD3, ADC_ERR_WATCHDOG);
+    }
+  }
 #if defined(STM32_ADC_ADC3_IRQ_HOOK)
   STM32_ADC_ADC3_IRQ_HOOK
 #endif
@@ -350,6 +362,8 @@ void adc_lld_start_conversion(ADCDriver *adcp) {
   adcp->adc->SR    = 0;
   adcp->adc->SMPR1 = grpp->smpr1;
   adcp->adc->SMPR2 = grpp->smpr2;
+  adcp->adc->HTR   = grpp->htr;
+  adcp->adc->LTR   = grpp->ltr;
   adcp->adc->SQR1  = grpp->sqr1 | ADC_SQR1_NUM_CH(grpp->num_channels);
   adcp->adc->SQR2  = grpp->sqr2;
   adcp->adc->SQR3  = grpp->sqr3;
diff --git a/os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.h b/os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.h
index 13df506..fa266f0 100644
--- a/os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.h
+++ b/os/hal/ports/STM32/LLD/ADCv2/hal_adc_lld.h
@@ -313,7 +313,8 @@ typedef uint16_t adc_channels_num_t;
  */
 typedef enum {
   ADC_ERR_DMAFAILURE = 0,                   /**< DMA operations failure.    */
-  ADC_ERR_OVERFLOW = 1                      /**< ADC overflow condition.    */
+  ADC_ERR_OVERFLOW = 1,                     /**< ADC overflow condition.    */
+  ADC_ERR_WATCHDOG = 2                      /**< ADC watchdog condition.    */
 } adcerror_t;
 
 /**
@@ -392,6 +393,16 @@ typedef struct {
    */
   uint32_t                  smpr2;
   /**
+   * @brief   ADC watchdog high threshold register.
+   * @details This field defines the high threshold of the analog watchdog.
+   */
+  uint16_t                  htr;
+  /**
+   * @brief   ADC watchdog low threshold register.
+   * @details This field defines the low threshold of the analog watchdog.
+   */
+  uint16_t                  ltr;
+  /**
    * @brief   ADC SQR1 register initialization data.
    * @details Conversion group sequence 13...16 + sequence length.
    */
@@ -531,6 +542,14 @@ struct ADCDriver {
 #define ADC_SMPR1_SMP_VBAT(n)   ((n) << 24) /**< @brief VBAT sampling time. */
 /** @} */
 
+/**
+ * @name    Threshold settings helper macros
+ * @{
+ */
+#define ADC_HTR(n)              ((n > ADC_HTR_HT) ? ADC_HTR_HT : n) /**< @brief High threshold limitation.  */
+#define ADC_LTR(n)              ((n > ADC_LTR_LT) ? ADC_LTR_LT : n) /**< @brief Low threshold limitation.   */
+/** @} */
+
 /*===========================================================================*/
 /* External declarations.                                                    */
 /*===========================================================================*/
--
2.7.4

Best regards,
Thomas

Re: PATCH: enable STM32/LLD/ADCv2 analog watchdog

Posted: Tue Jul 03, 2018 3:28 pm
by boehml
This post is quite old, but I tested this patch and it works just fine. Whats the point that it has not been merged yet?

Re: PATCH: enable STM32/LLD/ADCv2 analog watchdog

Posted: Tue Jul 03, 2018 3:43 pm
by Thargon
Hi,

I believe the line numbers do not match anymore but patching tools can handle simple shifts like this...

I think the reason why Giovanni did not merge this was maintenance. If this feature is part of the official ChibiOS framework, it needs to be officially tested and maintained. Unfortunately, Giovanni has moved some of that responsibility to the community, so these patches remain unofficial features.

Maybe I did get something wrong here, but then Giovanni will most probably correct me :)

- Thomas

Re: PATCH: enable STM32/LLD/ADCv2 analog watchdog

Posted: Tue Jul 03, 2018 6:23 pm
by faisal
There shouldn't be much maintainance overhead as this is confined to LLD. The point if LLD is to allow for platform specific features that are not in conflict with the upper level HAL driver.

Re: PATCH: enable STM32/LLD/ADCv2 analog watchdog

Posted: Tue Jul 03, 2018 9:14 pm
by Giovanni
Will look into this, my time is limited to weekends in this period.

Giovanni

Re: PATCH: enable STM32/LLD/ADCv2 analog watchdog

Posted: Sun Jul 08, 2018 3:08 pm
by Giovanni
Hi,

Added patch to trunk and 18.2.

Giovanni

Re: PATCH: enable STM32/LLD/ADCv2 analog watchdog

Posted: Mon Jul 09, 2018 8:16 am
by boehml
Nice. Thanks!