This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Compiler optimization breaks SAADC in SDK 15.3.0

Hello!

It seems to me that GCC compiler optimization (-O3 -g3) somehow break the SAADC.

When enabling said optimizations the SAADC no longer gives me valid measurements (e.g. I have an expected ADC value of 1200 but when enabling optimizations I get a value of 3).

Here you can find my code that I am using to measure the SAADC

This code is responsible for measuring the analog inputs 4 and 5.

The issue occours on both inputs. The numerical example I have given above is for Input 5.

I am aware of Anomaly 86 (https://infocenter.nordicsemi.com/index.jsp?topic=%2Ferrata_nRF52832_Rev2%2FERR%2FnRF52832%2FRev2%2Flatest%2Fanomaly_832_86.html&cp=3_1_1_0_1_23)

To avoid this issue I have slightly modified the nrfx_saadc_abort function to remove as seen below.

This change allows me to use this function to stop the SAADC as described in the anomaly without having to write my own code and it works just as expected if I have optimizations disabled.

I have been able to disable optimizations for the nrfx_saadc.c file by adding "#pragma GCC optimize("O0")" to the start of the file. This makes the SAADC measurement work again but it just doesn't feel right.

Are you aware of this issue and do you have any suggestions on what I should do to fix it?

Regards

Michael

Parents
  • Hi,

     

    What version of GCC are you using? LTO used?

    I have been able to disable optimizations for the nrfx_saadc.c file by adding "#pragma GCC optimize("O0")" to the start of the file. This makes the SAADC measurement work again but it just doesn't feel right.

    You're right to be worried.

    However, where does the corruption occur? Is it the float operation that fails, or is the nrfx call returning the incorrect value? It seems that you print only after the float conversion from the code snippets that you posted.

     

    Kind regards,

    Håkon

Reply
  • Hi,

     

    What version of GCC are you using? LTO used?

    I have been able to disable optimizations for the nrfx_saadc.c file by adding "#pragma GCC optimize("O0")" to the start of the file. This makes the SAADC measurement work again but it just doesn't feel right.

    You're right to be worried.

    However, where does the corruption occur? Is it the float operation that fails, or is the nrfx call returning the incorrect value? It seems that you print only after the float conversion from the code snippets that you posted.

     

    Kind regards,

    Håkon

Children
  • Hi and thanks for your reply!

    It's the nrfx call which fails. In the first code snippet above I am calling the `nrfx_saadc_sample_convert` function. That's where I already get the wrong data.

    When printing after the float conversion I am printing the previously received ADC value, as well as the newly calculated voltage value, if you look closely.

    For example I'd expect an ADC value of 1200, which I get if I have disabled the compiler optimizations. When enabling the optimizations I only get a value of 3.

    I am using GCC Version 7-2018-q2. Also, I have LTO disabled.

    Here you can see the part of my Makefile responsible for setting these flags, depending on the given CONFIGURATION

  • I am not 100 % sure that the workaround you have for implementing the calibration routine is water tight.

    Could you try this?

     

    PS: Note that you do not need to calibrate every time you do a conversion, unless there's a temperature change for instance or any other external change.

    Normally its OK if you calibrate on boot.

     

    Kind regards,

    Håkon