cancel
Showing results for 
Search instead for 
Did you mean: 

printf function call causes hard fault

Pramod K.G.
Associate II

Hi all,

I am working on a STM32F103VEtx MCU. In my firmware I have redirected the printf function to a UART for debugging purposes. When I start running the code, the printf function causes the hard fault handler to hit. Please see the call stack attached below

Thread #1 (Suspended : Signal : SIGINT:Interrupt)   

   prvGetRegistersFromStack() at stm32f1xx_it.c:109 0x800441a   

   <signal handler called>() at 0xfffffff9   

   std() at 0x8007abe   

   __sinit() at 0x8007b76   

   printf() at 0x8006dac   

   main() at main.c:130 0x800400c

0690X00000DXN5RQAX.png

It seems like  std() function call triggers the hard fault. Please help me to figure out and fix the issue.

Thanks in advance,

Pramod K. G.

10 REPLIES 10
TDK
Guru

Step through and figure out which instruction causes it. The standard printf uses malloc, which may be causing it.

If you feel a post has answered your question, please click "Accept as Solution".

Hi TDK,

Thanks for the response. I already had tried 'step through' the printf function and it was not working for me. ​Hardfault handler was hitting when I do a step in to printf function.

From the NVIC register CFSR, I could see that BFARVALID and PRECISERR are set. Also the content of BFAR is 0.

I tried with increasing the heap and stack but the results were same.​

It is telling you address 0 contains an invalid instruction. But you generally shouldn't be executing at address 0. Is it possible your vector table contains invalid (nullptr) entries and one of those interrupts is being called?
What happens if you disable irqs during the printf call?
If you feel a post has answered your question, please click "Accept as Solution".

Probably linking in the wrong libraries.

Do a disassembly/listing and walk the code.

I'd personally look at the CPU registers and code surrounding the failure.

Likely to be a Read as the fault is precise.

Perhaps a value in a structure or a pointer

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..

Thanks for looking into this issue.

Attaching the disassembly code snippet where issue is happening

         std:

08007ab9:  movs   r3, #0

08007abb:  push   {r4, lr}

08007abd:  mov    r4, r0

08007abf:  strd   r3, r3, [r0]

08007ac3:  str    r3, [r0, #8]

08007ac5:  strh   r1, [r0, #12]

08007ac7:  str    r3, [r0, #100] ; 0x64

08007ac9:  strh   r2, [r0, #14]

08007acb:  strd   r3, r3, [r0, #16]

It seems like hardfault is triggered from the line of code "08007abd:  mov    r4, r0". When clicking the std() function in call stack it is jumping to above mentioned line of code. Attaching the screenshot for more clarification.

0690X00000DXPHeQAP.png

A mov won't cause any fault, it's just moving a value of one register to another. It's most likely the next one, storing two words to memory pointed by [r0], which is the first parameter of the function call. So this function is called with a NULL pointer argument.

Get the sources of your C runtime library, and look into it, what could cause it to be called with a NULL pointer.

Thanks for the response.

can you please tell how can I get the sources of your C runtime library?

Ok, but what are the register values?

Betting R0 is NOT aligned and the STRD is failing

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..

Hi Clive1,

Attaching the general purpose resister values

r0   0   

r1   4   

r2   0   

r3   0   

r4   -171798145   

r5   0   

r6   0   

r7   12   

r8   115200   

r9   8   

r10   7   

r11   536871196   

r12   -171798145   

sp   0x2000017c <__global_locale+64>   

lr   0x8007b77 (Hex)   

pc   0x8007abe <std+6>   

xPSR   0x61000000 (Hex)   

msp   0x2000013c <__global_locale>   

psp   0x0   

primask   0   

basepri   0   

faultmask   0   

control   0  .

I am seeing weird behavior with sprintf also.

Eg.

sprintf(buff, (const char *)"sprintf testing\n\r"); => No issues

sprintf(buff, (const char *)"sprintf %d\n\r",10); => Hitting hard-fault

You said "Probably linking in the wrong libraries", can you please explain?

My Linker flags => -specs=nosys.specs -specs=nano.specs -u _printf_float