Skip to main content
Explorer
September 1, 2025
Solved

ADC Analog Watchdog (AWD) Interrupt-Disable and Enable again at Runtime

  • September 1, 2025
  • 3 replies
  • 932 views

I'm using the AWD (STM32G0B0CE) with the HAL_ADC_LevelOutOfWindowCallback(), which works fine.
For not blocking the MCU completely, I'm disabeling the AWD-IT inside the Callback when fired for about 500ms:
LL_ADC_DisableIT_AWD1 (ADC1);
After the 500ms elapsed the AWD-IT is enabled again:
LL_ADC_EnableIT_AWD1 (ADC1);

This only works fine for about 2 times:
Start -> Fire IT -> DisableIT
-> 500ms
-> EnableIT -> Fire IT -> DisableIT
-> 500ms
-> IT stays completely disabled, though enabled again.

Any idea what I'm missing?
Thanks.

    This topic has been closed for replies.
    Best answer by waclawek.jan

    ADC_CR.ADSTART can't be cleared by writing 0 to it; you stop conversions by setting ADC_CR.ADSTP and that in hardware clears ADC_CR.ADSTART. This is not immediate, you are supposed to read back ADC_CR.ADSTP until it autoclears.

    But I personally wouldn't do that. I would try to avoid triggering the interrupt by setting the watchdog thresholds so that no ADC result triggers it.

    JW

    3 replies

    Super User
    September 2, 2025

    > IT stays completely disabled,

    How do you know? Have you observed the respective control flags in ADC? A generic "interrupt does not fire" guide here. As you appear to use Cube/HAL, the problem may be also in Cube/HAL's fabric, I don't use it but it's open source so you can check yoruself.

    JW

    ETXAuthor
    Explorer
    September 7, 2025
    Thanks for your answer!
    Reading the reference manual (rm0454-stm32g0x0) about the ADC interrupt enable register (ADC_IER), it says AWD1IE (Analog watchdog 1 interrupt enable) can only be set, when ADSTART bit is cleared.
    The ADSTART bit is part of the ADC control register (ADC_CR) and is cleared by hardware after each conversion.
    As I'm running in continous conversion mode, I suppose ADSTART is never cleared by hardware.
    So tried to clear it manually while enabling AWD1IE again.
    ADC1->CR &= ~ADC_CR_ADSTART; // Clear ADSTART in ADC control register (ADC_CR)
    ADC1->IER|=ADC_IER_AWD1IE; // Enable AWD-interrupt in ADC IR enable register (ADC_IER)
     // LL_ADC_EnableIT_AWD1 (ADC1); // also doesn't work
    ADC1->CR |= ADC_CR_ADSTART; // Set ADSTART in ADC control register (ADC_CR)
    But unfortunately this does'nt also work, as clearing the ADSTART bit doesn't seem to work.
    As I'm just new to STM32 MCUs, maybe someone could give some more advice.
    Thanks!
    Super User
    September 7, 2025

    ADC_CR.ADSTART can't be cleared by writing 0 to it; you stop conversions by setting ADC_CR.ADSTP and that in hardware clears ADC_CR.ADSTART. This is not immediate, you are supposed to read back ADC_CR.ADSTP until it autoclears.

    But I personally wouldn't do that. I would try to avoid triggering the interrupt by setting the watchdog thresholds so that no ADC result triggers it.

    JW

    ETXAuthor
    Explorer
    September 7, 2025

    Thanks for your idea!
    This really sounds a better solution....