How to use NDEBUG?

This is more a general question.

In the source system_clock.c there is a check in SetSysClock() with an assertion:

error("SetSysClock failed\n");

But when enter in this condition (by forcing) there is nothing at the serial port about error information and the code stops.

if I go to mbed_error.c I see that something is executed when:

#ifndef NDEBUG

I already tried #undef NDEBUG in the c-file or “target.macros_add”: [“NDEBUG=1”] in the target_overrides but no effect. In that stage a printf is also not working.

There is nothing to find about the correct use of NDEBUG and how to make error information visible in case of debugging.

Any suggestion?


I do not know exact answer to your question but I suppose you are struggling with wrong clock settings.

I do not know what exactly you expect you will see but when the code reach this line that means that you have wrong clock settings and every attempt (when you have active all 3, then the board can try one by one) above failed, nothing more. So you need to step into clock settings and check which HAL function returned zero. That tell you which part of settings is probably wrong.

In official is just MSI I suppose you fill another from CUBEMX according to your board.

BR, Jan

I’m not struggeling with the clock settings anymore but just wanted to know how you can read the error messages if they would be reached. I see error(…) at several places in the code but how to turn on/off these messages? Just to know because when I have to debug something else i’ts handy to know the procedure. Otherwise the controller is just hanging and you don’t know where and why.

Aha, ok then.

It seems it has something together with build profiles. So so it should change depending on the selected profile

BR, Jan

In those links I don’t see any info how to use it. NDEBUG is somewhere defined by default? Do you have to adapt the Cmake file? You set it on and off per module or only globally? Will it work with stdio with the speed and pins defined in your config? Only questions about something looking very essential.

How I already wrote it is about build profiles. There exist debug, develop and release profile and the NDEBUG should be probably set automatically set when you chose release profile.

BR, Jan

Ah ok I see it’s just an option in mbed-tools compile. If I try to do:

Deliberate insert an error:

MBED_WEAK void SetSysClock(void)

Compile with debug option

mbed-tools compile --clean --profile debug -m HMC20 -t GCC_ARM

It looks like the error is neglected. The code runs as before. If I ommit the --profile debug, the code halts on this point with no serial data.

Results are not constentent.
Between each test I also did a hardware reset:

Compile with error(“Test\n”) and no debug option → hanging
Compile with error(“Test\n”) and debug option → hanging
Compile with //error(“Test\n”) and no debug option → Hello world
Compile with //error(“Test\n”) and debug option → Hello world

In the opposite direction I get Hello world until the second line.
It means the behavior of using the debug option is following the last result when compiling without debug option.

To be honest I never used profiles but maybe is necessary to re-compile whole project (I do not know if this is happening automatically when you change the profile in ARM Mbed).

I tried that with MbedCE because I do not use any Mbed offline solution anymore, just KeilsStudioCloud for some help to others.

// I placed this directly to main immediately after a printf with a Start string

// Console output with Debug profile

++ MbedOS Error Info ++
Error Status: 0x80FF0100 Code: 256 Module: 255
Error Message: Fatal Run-time error
Location: 0x8006DC7
Error Value: 0x0
Current Thread: main Id: 0x20002B44 Entry: 0x8006AF5 StackSize: 0x1000 StackMem: 0x20001B20 SP: 0x20002A9C 
For more info, visit:
-- MbedOS Error Info --

// Console output with Release profile

// Console output with Develop profile is same like first one (Debug)

In all cases the program hangs of course and is re-builded (not clean) and recompiled.

BR, Jan

Can you put the error line on the same location that I did? In the clock config. I think if this error is called before uart is initialized that nothing happens.

I found the root cause in my case. I always use this command:

mbed-tools compile --clean --profile DEBUG -m HMC20 -t GCC_ARM && (FILE=./cmake_build/HMC20/develop/GCC_ARM/hmc20_test.bin; python3 $FILE; st-flash --freq=4M --reset write $FILE 0x8000000)

But if I compile with debug option, another directory is generated:


It means that I am programming the wrong bin file.

I have to change the path:


For the reason I call ‘append’ see my ticket [STM32U575RGT6]: Verification failed at offset 43008 · Issue #1362 · stlink-org/stlink · GitHub

Important to know: The default profile is ‘develop’ when no --profile option is given in the command.
If you are using --clean, only the relevant folder is cleaned. It means --clean with --profile debug, the folder debug is rewritten and the folder develop is untouched.

That’s the cause of the strange ‘memory’ behavior.

When I put debug() and error() in main:

In development profile I see debug() and error() messages.
In debug profile I see debug() and error() messages.
In release profile I see none of them, but firmware hangs.

This is only working when putting debug() and error() messages in main function as test.
If you put error(“Test\n”) when entering the SetSysClock in system_clock.c you see no error message in all cases. Even if I put a printf(“Test\n”) at this location, the firmware hangs.

So what is the sense to put an error in the code error(“SetSysClock failed\n”) in system_clock.c?
What’s the reason that printf() and error() is not working in system_clock.c?

It looks like you cannot execute error() before the call of mbed_rtos_start();

I did it and the result is same as before

// with debug...
++ MbedOS Error Info ++
Error Status: 0x80FF0100 Code: 256 Module: 255
Error Message: Fatal Run-time error
Location: 0x8000329
Error Value: 0x0
Current Thread: <unnamed> Id: 0x0 Entry: 0x8004AFF StackSize: 0x0 StackMem: 0x800031D SP: 0x2001FF74 
For more info, visit:
-- MbedOS Error Info --

// and so on

To be honest no output in console before clock setting is done is more logical for me but I don’t understand this so deep.

BR, Jan

I have different results. If I put the error(“Test\n”) in main after another printf and compile with debug option I get (as you have) the error in the terminal as expected. If I put error(“Test\n”) in the beginning of SetSysClock funtion, the firmware hangs at that point without anything in the console window. There may be differences in CPU, compiling option etc. I can understand that the error() lines are there to be generic and may work in certain circumstances but this is clearly not always guaranteed.

Maybe another reason could be is that you use different pins for stdio (the standard ones?) and I use a dedicated setting.

I use standard Nucleo board so the UART what is predefined because ti si connected to the onboard ST-link.

BR, Jan

I use my own hardware and retargetted the stdio:


One of the things I think on is that is may be possible that this error data is coming out to a different pin and once in main to the pin where my FTDI is connected on. I will make a variant of the same HW (more generic) where I can better test it. But I will not loose too much time because it’s a non blocking issue. :wink:

Yeah, I remember you have your own board.
If you do not use any retargeting somewhere (like in mbed_app.json) then the output should be PB_6/PB_7

BR, Jan

I redirected to PB6/7, in my case the default was different. I remember that in my first trial the serial data was coming out somewhere on the usb pins.

What’s the reason that printf() and error() is not working in system_clock.c?