Program points to null in disassembly while debugging

Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

cross mob
lock attach
Attachments are accessible only for community members.
SAJO_1338106
Level 4
Level 4
25 replies posted 10 replies posted 5 replies posted

While debugging my program, I found that the pointers gets lost and could not trace the current statement when halted. Disassembly opens and points to one of the sub routine. Note that I have I2C sensors connected. They gave output as follows at the USBUART:

"Temp = 26580 Humidity = 35596 UV = 1 LW = 65533 IR = 65535

HDR Address 64 Temperature = 00046,0223124215, 0.00, 0.00, 0.00, 0.00, 0.00, 0.00, 0.00, 0.00, 0.00, MPPT A = 40 B = 35 C = 38 D = 36 Pmax A = 88 B = 86 C = 85 D = 29 Temp = 26584 Humidity = 35468 UV = 0 LW = 65534 IR = 0

HDR Address 64 Temperature = 00046,0223124225, 0.00, 0.00, 0.00, 0.00, 0.00, 0.00, 0.00, 0.00, 0.00, MPPT A = 49 B = 35 C ="

But all of the sudden, it program window opens to Disassembly and I could not see the program pointer. Though I can run and halt but nothing happens.

"

673:                                    

674:                                        if((atoi(hour)> 7) && (atoi(hour)<19) && (RTC_1_ReadMinute() != (u_short)atoi(min)))

0x0000172E add r0, sp, #54 ; 0x54

0x00001730 bl d6a0 <atoi>

0x00001734 cmp r0, #7

0x00001736 ble.n 1790 <CYDEV_DMA_SRAM16K_MSIZE+0x790>

0x00001738 add r0, sp, #54 ; 0x54

0x0000173A bl d6a0 <atoi>

0x0000173E cmp r0, #12

0x00001740 bgt.n 1790 <CYDEV_DMA_SRAM16K_MSIZE+0x790>

0x00001742 bl 464c <RTC_1_ReadMinute>

0x00001746 mov r5, r0

0x00001748 add r0, sp, #58 ; 0x58

0x0000174A bl d6a0 <atoi>

0x0000174E uxth r0, r0

0x00001750 cmp r5, r0

0x00001752 beq.n 1790 <CYDEV_DMA_SRAM16K_MSIZE+0x790>

675:                                        {

676:                                            RTC_1_WriteMinute((u_short)atoi(min));

0x00001754 add r0, sp, #58 ; 0x58

0x00001756 bl d6a0 <atoi>

0x0000175A uxtb r0, r0

0x0000175C bl 4604 <RTC_1_WriteMinute>

677:                                            UART_1_PutString("Minutes updated\n");

0x00001760 ldr r0, [pc, #1cc] ; (1930 <CYDEV_DMA_SRAM16K_MSIZE+0x930>)

0x00001762 bl 4d54 <UART_1_PutString>

678:                                            EEPROM_1_UpdateTemperature();

0x00001766 bl 5090 <EEPROM_1_UpdateTemperature>

679:                                            EEPROM_1_Write2Byte((u_short)atoi(date)*100+(u_short)atoi(hour),SYNC_ADDRESS);

0x0000176A add r0, sp, #5c ; 0x5c

0x0000176C bl d6a0 <atoi>

0x00001770 mov r5, r0

"

Output window log:

"

Device 'PSoC 5LP CY8C5868AXI-LP035' was successfully programmed at 02/24/2020 18:01:18.

Continuing target program

The target program has stopped at: file: main.c line: 904 function: main address: 0x00001BF8

Continuing target program

The target program has stopped at: file: main.c line: 1056 function: main address: 0x00002018

Continuing target program

The target program has stopped at: file: main.c line: 674 function: MyRxInt address: 0x0000172E

Continuing target program

The target program has stopped at: file:  line: -1 function: USBUART_TABLE address: 0x0003EF74

Continuing target program

The target program has stopped at: file:  line: -1 function: USBUART_TABLE address: 0x0003EF74

Continuing target program

The target program has stopped at: file:  line: -1 function: USBUART_TABLE address: 0x0003EF74

Continuing target program

The target program has stopped at: file:  line: -1 function: USBUART_TABLE address: 0x0003EF74

Continuing target program

The target program has stopped at: file:  line: -1 function: USBUART_TABLE address: 0x0003EF74

Continuing target program

The target program has stopped at: file:  line: -1 function: USBUART_TABLE address: 0x0003EF74

Continuing target program

The target program has stopped at: file:  line: -1 function: USBUART_TABLE address: 0x0003EF74

"

Please find the attachment containing my project.

Appreciate any assistance.

0 Likes
1 Solution

Hi Motoo, Len,

The problem was with the strcat. After using the first sprintf(disp,"S%.5u,", index) ; resolved the global variable issue. We can safely say that the root cause of the problem was the sprintf in ISR. After moving them to main.c and changing %f to %d resolved the stack overflow issue.

But I wonder why %f fails when the length of the sprintf is more i.e. 100+ bytes  even after increasing the heap size to even 0x2000. Main issue is certainly now with the stack or heap size but the %f function itself.

View solution in original post

36 Replies
Rakshith
Moderator
Moderator
Moderator
250 likes received 1000 replies posted 750 replies posted

Hi SAJO_1338106​,

When I build the project I am getting an error stating that some files are missing as shown - pastedImage_0.png

I was unable to find FS.h in the archive shared.

pastedImage_1.png

Can you please re-attach the project?

Thanks and Regards,

Rakshith M B

Thanks and Regards,
Rakshith M B
0 Likes
lock attach
Attachments are accessible only for community members.

Hi Rakshith,

Could you please try now? I have reattached the my project.

0 Likes

Hi Rakshith,

Just follow the instruction given in the datasheet of the emfile component

to generate FS.h.

When using the GCC toolchain, you must specify the directory where the

library file is located.

The steps to create the emFile project for PSoC 5LP application using GCC

toolchain are as

follows:

1. Decide which library you need. This decision is based on whether you

need FAT12/16 or

FAT32, whether your application uses an OS, and whether you need long file

name

support. This example uses emf32nosnlfn.lib (FAT32, no OS, and no long file

name

support).

2. Select the necessary include file directory. Go to Project > Build

Settings > ARM GCC

4.8.4 > Compiler > General. Click the “…” button in the Additional Include

Directories

property field. The Additional Include Directories dialog will display.

Click the New

button and select an include directory for PSoC 5 and an include directory

for the specific

options you want.

Note If want to run the project in both “Debug” and “Release”

configurations you need to

add the Include Directories for both configurations.

3. Go to Project > Build Settings > ARM GCC 4.8.4 > Linker > General >

Additional

Library Directories. Click the “…” button in the Additional Library

Directories property

field.

The Additional Library Directories dialog will display.

4. Click the New button and select the library directory for the GCC

library.

Adding Library Directory

5. Specify the library in the library directory.

a. Go to Project > Build Settings > ARM GCC 4.8.4 > Linker > General >

Additional

Libraries.

b. Type in the library name without prefix "lib" and suffix ".a" (for

example,

"libemf32nosnlfn.a" would be "emf32nosnlfn"). This is because GCC

compiler will automatically add the “lib” prefix to the library name.

Note If want to run the project in both “Debug” and “Release”

configurations you need to

add the Link library for both configurations.

6. If usage of OS or logging feature is desired then FS_ConfigIO.c or FS_X_OS.c

files

should be added to the project. Details on OS integration and logging

feature usage can

be found in the emFile User Guide in Chapters 8 and 9 respectively.

The mentioned files can be added directly into your project from the

Code/Source/PSoC5

directory or copied first to your project directory and added from there.

The files will

usually be edited, so you need to decide whether to change the original

files or a copy

that is specific to the project.

The files are added to the project using Project > Existing Item.

Add <FS.h> header file in your main.c function.

0 Likes
Len_CONSULTRON
Level 9
Level 9
Beta tester 500 solutions authored 1000 replies posted

SAJO,

I was finally able to get your project to compile.  I'm having difficulties getting your program to run since I don't have the right CPU or the same peripherals.

However, I noticed the following:

  • Flash used: 259928 of 262144 bytes (99.2 %).  SRAM used: 54441 of 65536 bytes (83.1 %). Stack: 4096 bytes. Heap: 512 bytes.
    Wow! This is a VERY FULL program.  You're using 99.2% of FLASH and 83.1% of SRAM.    Suggestion:  Can you reduce your SRAM requirements and increase your Stack and your heap?  You might be running out of stack or heap.
  • I noticed you have 6 ISRs.  I also noticed you are performing a lot of processing in some of them including CyDelay()s.  I hope you don't mind a recommendation from someone with years of experience in embedded design.  I learned LONG AGO (30+ years) from a mentor, always write your interrupt code small and tight.  If you spend too much time in the interrupt, you might lose the next interrupt.  Always get the data or signal that caused the interrupt and signal back to the task level (main.c in your case) that the signal occurred or the data is now stored in a buffer.

Having said that:  Here's a tool to use in the debugger.  Sometimes it can be a big help when the code "goes off in the weeds".

When you stop the debugger (manually or using a breakpoint) notice the "Call Stack" tab.  It should indicate the levels of stack at the stop point up to main().

Once I re-targetted your project to the Device being used for the CY8CKIT-059 board, I got your project running-ish.  Since I don't have your peripherals it is limited.

What are you using to communicate (HMI) with the application?  UART_1 or USBUART?   I'd say it was UART_1 since you have a UART_1_GetChar().  It does look like you are using USBUART as a output.

Len

Len
"Engineering is an Art. The Art of Compromise."

Hi Len,

Advice well taken.

Stack overflow could be the reason.  I am storing the results in flash so it is almost full.

I2C devices are required to run the code. I am using ESP for wireless communication and downloading the results through UART and USB for debugging purpose. Program would run without USB.

I will decrease the ISR task and re code it in main.c and let you know the results.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi,

Reading your main.c, I felt a little bit uneasy about sprintfs.

By any chance, can you replace all

  sprintf(disp,

with

  snprintf(disp, 150,

and try if it still caused problem?

moto

0 Likes

Hi Moto,

Any specific reason to use snprintf instead of sprintf? I have ensured that the total bytes never exceeds 132 bytes.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi, SaJo-san,

At first I was afraid that there could be a case the total exceeds 150.

So it may not help at all.

Following are idea(s) off my head... (so may not be quite convincing)

Before I had an experience with smaller device (PSoC 4)

when the number of arguments exceeded 5 or 6 sprintf caused malfunction of the application.

(The length of buffer was enough.)

So, I also may try to reduce the length of disp[] and make more sprintf and UART_1_PutString couples.

(This also release some sram but may consume more flash)

and/or I would  create and try an onion skin function something like

============

#define TIMEOUT_LIMIT 5000

my_print(char *str)

{

    uint16_t timeout_count  = 0 ;

    UART_1_PutString(str) ;

    while(UART_1_GetTxBufferSize()) {

        timeout_count++ ;

        if (timeout_count > TIMEMOUT_LIMIT) {

            break ;

        }

       CyDelayUs(1) ;

    }

}

============

moto

HI Moto,

Yes, this will reduce the SRAM(16% RAM is still available to handle these)

but I think that the issue could be something else because the debugger is

clueless about the current operating statement. Debugger suppose to have

the track recorder of what are the previous states. Strange that the

debugger is of no help in this scenario. Anyway, I am rewriting code as Len

suggested and share my results.

On Tue, Feb 25, 2020 at 10:38 AM Motoo Tanaka <community-manager@cypress.com>

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi, Sajo-san,

I'm sorry for missing the point.

I hope you will be successful with the rewrite.

moto

0 Likes

SAJO,

As moto pointed out snprintf() is preferred over sprintf() because it is considered safer by ANSI C.  The 'n' in snprintf() prevents accidentally overwriting beyond the allocated string size thus preventing corrupting RAM.

It's great that you're counting the size of the string.  I have on too many occasions just slapped together a sprintf() without counting and found I didn't allocate a large enough string.  Then I wondered why my code went off into the weeds or some variable was nowhere close to what it is suppose to be.

Len

Len
"Engineering is an Art. The Art of Compromise."

Hi Len,

Keeping that issue in mind, I had kept extra 20 bytes. Till now, the maximum length was 118 bytes.

Hi Moto,

Glad that you brought this new function snprintf.

Hi Len, Moto,

It is been one and half days on the debugger and still running with the following changes.

  1. I cut short the ISR of RX and moved the task to main.c
  2. Set the master clock to 24 MHz
  3. Stack: 8192 bytes. Heap: 4096 bytes

No issues till now except some UART send receive functionality delay which needs to be worked out with ESP. However, I am still surprised to encounter same issue when the master clock is set to 48 MHz. Am I still missing something here? Is it because of GPIO limitation?  Is there any other alternatives to CyDelay which Len mentioned that I am using so many times which could cause an issue? Kindly advise.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Dear Sajo-san,

I just reopened your original project and played with the DWR > Clocks

To support USB, the device has very accurate 24MHz IMO +/- 0.25%

000-IMO-24MHz.JPG

But if I changed it to 48MHz the accuracy is now +/- 5% which is about the limit of UART to work correctly

001-IMO-48MHz.JPG

and also if you are using USB, the accuracy is not acceptable.

003-IMO-48MHz.JPG

I wonder if you use IMO 24MHz and use PLL to make it 48MHz, will it make it work better?

002-IMO24-PLL48.JPG

Best Regards,

27-Feb-2020

Motoo Tanaka

0 Likes

Hi Motoo,

Setting was exactly similar. I increased the PLL to 48 MHz and USB to IMOx2. Program pointer gets last after a couple of main program execution.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Dear Sajo-san,

> Setting was exactly similar. I increased the PLL to 48 MHz and USB to IMOx2.

> Program pointer gets last after a couple of main program execution.

Oh, you've done it.

Another thing I would try is to divide the Bus Clock by 2 = 24Mhz, but still keep Master Clock 48MHz

004-bus-24.JPG

In advance, if this does not help, I'm sorry.

Best Regards,

27-Feb-2020

Motoo Tanaka

Hi Moto,

Is the XTAL 32kHz clock generated from the IMO?  I also have a crystal oscillator of 32kHz in my PCB. Let me know. I will try your suggestion now.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi,

IMO can be generated from XTAL but I'm afraid that it can not be generated from XTAL 32kHz.

moto

0 Likes

Hi Moto,

Your suggestion is working fine now. I reduced the bus frequency to 24 MHz and rest to 48 MHz. I will keep it running for some more time and let you know if I encounter any issue.

0 Likes

Hi Len, Moto,

I encountered the same issue now.

Program counter

0x00000000 <RomVectors>:

  40: Disassembly of section .text:

0x00000000 ... ....9B..9B..

0x00000010 <Reset>:

  55: *  This function handles the reset interrupt for the GCC toolchain. This is the

  56: *  first bit of code that is executed at startup.

  57: *

  58: *******************************************************************************/

  59: void Reset(void)

  60: {

0x00000010 push {r3, lr}

  69:         #endif /* (CYDEV_DEBUGGING_ENABLE) */

  70:         /* Reset Status Register has Read-to-clear SW access mode.

  71:         * Preserve current RESET_SR0 state to make it available for next reading.

  72:         */

  73:         *(reg32 *)(CYREG_PHUB_CFGMEM23_CFG1) = *(reg32 *)(CYREG_RESET_SR0);

0x00000012 ldr r3, [pc, #10] ; (24 <CYDEV_CHIP_REVISION_4G_ES2+0x3>)

0x00000014 ldr r2, [r3, #0]

0x00000016 add.w r3, r3, #2fc0 ; 0x2fc0

0x0000001A adds r3, #2

0x0000001C str r2, [r3, #0]

  82:     #if ((CYDEV_BOOTLOADER_ENABLE) && (CYDEV_PROJ_TYPE != CYDEV_PROJ_TYPE_LOADABLEANDBOOTLOADER))

  83:         CyBtldr_CheckLaunch();

  84:     #endif /* ((CYDEV_BOOTLOADER_ENABLE) && (CYDEV_PROJ_TYPE != CYDEV_PROJ_TYPE_LOADABLEANDBOOTLOADER)) */

  85:     Start_c();

0x0000001E bl 4278 <Start_c>

0x00000022 nop

0x00000024 .word 0x400046fa

0x00000028 <__do_global_dtors_aux>:

0x00000028 push {r4, lr}

0x0000002A ldr r4, [pc, #14] ; (40 <CY_METADATA_SIZE>)

0x0000002C ldrb r3, [r4, #0]

0x0000002E cbnz r3, 3e <CYDEV_MFGCFG_ANAIF_SIZE+0x6>

0x00000030 ldr r3, [pc, #10] ; (44 <CY_METADATA_SIZE+0x4>)

0x00000032 cbz r3, 3a <CYDEV_MFGCFG_ANAIF_SIZE+0x2>

0x00000034 ldr r0, [pc, #10] ; (48 <CY_METADATA_SIZE+0x8>)

0x00000036 nop.w

0x0000003A movs r3, #1

0x0000003C strb r3, [r4, #0]

0x0000003E pop {r4, pc}

0x00000040 .word 0x1fff8370

0x00000044 .word 0x00000000

0x00000048 .word 0x0000fd2c

Call stack log

0 appl1_start() ?????? ?????? 0x00000000 (All)

1 <signal handler called>() ?????? ?????? 0xFFFFFFF1 (All)

2 appl1_start() ?????? ?????? 0x00000000 (All)

3 <signal handler called>() ?????? ?????? 0xFFFFFFF9 (All)

4 __lshift() ?????? ?????? 0x0000F672 (All)

5 ??() ?????? ?????? 0x00000000 (All)

Register status

r0=,0xF8000000,r1=,0x201EDC34,r2=,0xFFFFFFFF,r3=,0x201EDC54,r4=,0x00000000,

r5=,0x4B04B509,r6=,0x4B04B508,r7=,0x1FFF82D0,r8=,0x00000020,r9=,0x0000001B,

r10=,0x201EDC50,r11=,0xFFFFFFFE,r12=,0x00000005,sp=,0x20007B30,lr=,0xFFFFFFF1,

pc=,0x00000000,xpsr=,0xA0000003,msp=,0x20007B30,psp=,0x00000000,

0 Likes

SAJO,

From your last email it is evident that your code 'train' "went off the tracks".  Sadly, the Call stack log does not indicate where the last call to valid code was made.

Debugging is going to be a bit more complicated. 

Just before the code crashes, is there anything specific that is happening?  For example: user input, user output?

There are MANY reasons why code can crash.  Stack over runs.  Out of bounds array processing.  Nested interrupts, overly-recursive functions. Just to name a few.

Does your program always crash to the same place (ie: void Reset(void))?

Although it would be great to use the debugger, it appears not to be of help YET.  It would be great if the call stack had a valid location.  This would be effectively the last place the code was 'sane'.  If this valid location was consistently the last sanity point, you could inspect/review the code executed before it.  Additionally, you could put a breakpoint in the code immediate following the last sanity point.  With that you might be able to inspect the variables passed to see what might have happened.

Another debugging tip is to leave 'breadcrumbs'.  You can place external signals in your code to read these signals using a scope.  For example, you are using a I2C device.  With this, you can see every time I2C is occurring.  If you put thoughtfully placed calls to GPIO pin(s) to toggle at certain points this might be helpful.  If there is a consistent pattern, you might find where in the sequence of signals the breakdown occurs.

The goal of the 'signal' strategy above is to try to reduce the places in your code where the problem may be.  If this is effective, then you can more quickly found the root cause.

Question:  Are you enabling the Watchdog?

I hope this helps.  I've found that these moments where the issue is complex to solve helped to build my trouble-shooting skills which in itself is a valuable skill.  The lessons learned from a successful root cause analysis in turn became improvements to my design skills.

Len

Len
"Engineering is an Art. The Art of Compromise."
0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Dear Sajo-san,

I'm a little bit slow and was not reading everything carefully,

and I just noticed the following line.

> and USB for debugging purpose. Program would run without USB.

If this is the case, can you replace USBUART with another UART, such as UART_2 ?

As you know, USB takes up a lot of memory and CPU power, just replacing USBUART

with a simple UART and connect a USB-Serial converter something like below

may make the situation better.

UMFT234XF FTDI, Future Technology Devices International Ltd | 集積回路(IC) | DigiKey

Best Regards,

27-Feb-2020

Motoo Tanaka

0 Likes

Hi Motoo, Len,

I increased the stack size and heap size (Stack -16384 bytes. Heap: 4096 bytes.) and did not connect USB(hence USBUART component was not running). Though I faced the same situation of hanging in the disassembly, I was able to record the stack call as follows:

0 __lshift() ?????? ?????? 0x0000F628 (All)

1 _dtoa_r() ?????? ?????? 0x0000EF58 (All)

2 __cvt() ?????? ?????? 0x0000DBD6 (All)

3 _printf_float() ?????? ?????? 0x0000DD9E (All)

4 _svfprintf_r() ?????? ?????? 0x0000FC00 (All)

5 sprintf() ?????? ?????? 0x0000E49C (All)

6 display_content(uint8 index = <optimized out>, uint8 mode = 0 '\000', uint8 mode@entry = 0 '\000') main.c 356 0x00000BC0 (All)

7 TimerInt4() main.c 570 0x000014BA (All)

8 <signal handler called>() ?????? ?????? 0xFFFFFFF9 (All)

9 CyDelayCycles_loop() Generated_Source\PSoC5/CyBootAsmGnu.s 48 0x000099F8 (All)

10 CyDelay(uint32 milliseconds = 10, uint32 milliseconds@entry = 10) Generated_Source\PSoC5\CyLib.c 1471 0x00004550 (All)

11 main() main.c 1169 0x0000268C (All)

Assembly code and the current point location is in bold.

0x0000F60C <__lshift>:

0x0000F60C stmdb sp!, {r4, r5, r6, r7, r8, r9, sl, lr}

0x0000F610 mov r4, r1

0x0000F612 mov r7, r0

0x0000F614 mov r9, r2

0x0000F616 ldr r6, [r4, #10]

0x0000F618 mov.w sl, r2, asr #5

0x0000F61C add r6, sl

0x0000F61E ldr r1, [r1, #4]

0x0000F620 ldr r3, [r4, #8]

0x0000F622 adds r5, r6, #1

0x0000F624 cmp r3, r5

0x0000F626 bge.n f62e <__lshift+0x22>

0x0000F628 adds r1, #1

0x0000F62A lsls r3, r3, #1

0x0000F62C b.n f624 <__lshift+0x18>

0x0000F62E mov r0, r7

0x0000F630 bl f294 <_Balloc>

0x0000F634 movs r3, #0

0x0000F636 mov r8, r0

0x0000F638 mov r2, r3

0x0000F63A add.w r1, r0, #14

0x0000F63E cmp r3, sl

0x0000F640 bge.n f64a <__lshift+0x3e>

0x0000F642 str.w r2, [r1, r3, lsl #2]

0x0000F646 adds r3, #1

0x0000F648 b.n f63e <__lshift+0x32>

0x0000F64A bic.w r3, sl, sl, asr #1f

0x0000F64E ldr r0, [r4, #10]

0x0000F650 add.w r3, r1, r3, lsl #2

0x0000F654 ands.w r9, r9, #1f

0x0000F658 add.w r1, r4, #14

0x0000F65C add.w lr, r1, r0, lsl #2

0x0000F660 beq.n f68c <__lshift+0x80>

0x0000F662 rsb ip, r9, #20

0x0000F666 movs r2, #0

0x0000F668 ldr r0, [r1, #0]

0x0000F66A mov sl, r3

0x0000F66C lsl.w r0, r0, r9

0x0000F670 orrs r2, r0

0x0000F672 str.w r2, [r3], #4

0x0000F676 ldr.w r2, [r1], #4

0x0000F67A cmp lr, r1

0x0000F67C lsr.w r2, r2, ip

0x0000F680 bhi.n f668 <__lshift+0x5c>

0x0000F682 str.w r2, [sl, #4]

0x0000F686 cbz r2, f69a <__lshift+0x8e>

0x0000F688 adds r5, r6, #2

0x0000F68A b.n f69a <__lshift+0x8e>

0x0000F68C subs r3, #4

0x0000F68E ldr.w r2, [r1], #4

0x0000F692 cmp lr, r1

0x0000F694 str.w r2, [r3, #4]!

0x0000F698 bhi.n f68e <__lshift+0x82>

0x0000F69A subs r5, #1

0x0000F69C mov r0, r7

0x0000F69E str.w r5, [r8, #10]

0x0000F6A2 mov r1, r4

0x0000F6A4 bl f2fe <_Bfree>

0x0000F6A8 mov r0, r8

0x0000F6AA ldmia.w sp!, {r4, r5, r6, r7, r8, r9, sl, pc}

Problem seems to be with float printing I guess.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Dear Sajo-san,

That printf is called from an ISR, TimerInt4.

IMHO, using printf/sprintf inside an ISR is not a safe operation.

By any chance can you only set a flag in the TimerInt4 and

print (call the display_content()) outside of the ISR?

Best Regards,

10-Mar-2020

Motoo Tanaka

Hi Motoo,

I have removed timer 4. The subroutine under timer 4 is moved to main.c. I will post the results soon. Hope that this might resolve the issue.

Hi Motoo,

Still the problem remains but current program pointer going at the beginning of the main function. Still do not understand what is going wrong.

0 Likes

After moving the timer subroutine to main.c, I got the same call stack trace.

0 appl1_start() ?????? ?????? 0x00000000 (All)

1 <signal handler called>() ?????? ?????? 0xFFFFFFF1 (All)

2 appl1_start() ?????? ?????? 0x00000000 (All)

3 <signal handler called>() ?????? ?????? 0xFFFFFFF9 (All)

4 __lshift() ?????? ?????? 0x0000F48C (All)

5 _dtoa_r() ?????? ?????? 0x0000ED68 (All)

6 __cvt() ?????? ?????? 0x0000D9E6 (All)

7 _printf_float() ?????? ?????? 0x0000DBAE (All)

8 _svfprintf_r() ?????? ?????? 0x0000FA10 (All)

9 sprintf() ?????? ?????? 0x0000E2AC (All)

10 display_content(uint8 index = <optimized out>, uint8 mode = 0 '\000', uint8 mode@entry = 0 '\000') main.c 355 0x00000BC8 (All)

11 main() main.c 1380 0x00002C18 (All)

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Dear Sajo-san,

From the stack trace, what I can say are

(1) display_content(index=?, mode=0) was called at main.c line 1380

(2) sprintf() was called from display_content

(3) _svprintf() was called from sprintf()

(4) _print_float() was called from _svprintf()

...

So the first exception happened in the _print_float(),

which means one of the "%f" triggered the exception.

Since the "mode" was 0 following line was called

============

        len = sprintf(disp,"\r%u %.5u,%ld,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%2.2f,%2.2f,%d,%d,%d\n",sizeof(flash_dump), index,flash_dump.day_seq,(float32)flash_dump.I1,(float32)flash_dump.V1/1000,(float32)flash_dump.I1*flash_dump.V1/1000,(float32)flash_dump.I1,(float32)flash_dump.V1/1000,(float32)flash_dump.I2*flash_dump.V2/1000,(float32)flash_dump.I3,(float32)flash_dump.V3/1000,(float32)flash_dump.I3*flash_dump.V3/1000,(float32)flash_dump.I4,(float32)flash_dump.V4/1000,(float32)flash_dump.I4*flash_dump.V4/1000,(float32)flash_dump.Vbat/1000,temperature,humidity,flash_dump.U_V,flash_dump.LW,flash_dump.MIR);

============

To test the behaviour of this line, I created a test project and  copied variable definitions and display_content()

(I used CY8CKIT-059).

The output was

010-TeraTerm-log.JPG

And something was wrong here, as you have 21 arguments in the sprintf's format

1: sizeof(flash_dump),

2: index,

3: flash_dump.day_seq,

4: (float32)flash_dump.I1,

5: (float32)flash_dump.V1/1000,

6: (float32)flash_dump.I1*flash_dump.V1/1000,

7: (float32)flash_dump.I1,

8: (float32)flash_dump.V1/1000,

9: (float32)flash_dump.I2*flash_dump.V2/1000,

10: (float32)flash_dump.I3,

11: (float32)flash_dump.V3/1000,

12: (float32)flash_dump.I3*flash_dump.V3/1000,

13: (float32)flash_dump.I4,

14: (float32)flash_dump.V4/1000,

15: (float32)flash_dump.I4*flash_dump.V4/1000,

16: (float32)flash_dump.Vbat/1000,

17: temperature,

18: humidity,

19: flash_dump.U_V,

20: flash_dump.LW,

21: flash_dump.MIR

But the last argument correctly written was

  No.16 :   (float32)flash_dump.Vbat/1000,

and

No.17: temperature,

was only written as "-"

Then I noticed that I have not enlarged the heap size so it was 0x80

and I enlarged it to 0x200, then data was printed correctly.

012-TeraTerm-log.JPG

So in your application's case, you have already set the heap size as 0x200,

but may be you need to enlarge it more.

Meantime, if you have time and patience, please refer to my old memo

printf and float rhapsody (aka, yet another printf and floating topic)

In general, I'd rather avoid using "%f" and use "%d.%02d" trick in the above memo.

And if you will still have the same problem, how about temporary rewriting the display_content() just like

==================

uint8 display_content(uint8 index, uint8 mode)

{

    uint8 len;

    char buf[32] ;

   

    if(mode)

    {

        temperature = (temp[index]*0.0025177001953125 - 40); humidity = humid[index]*0.00152587890625;

        len = sprintf(disp,"%.5u,%.2u%.2u%.2u%.2u%.2u,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%5.2f,%2.2f,%2.2f,%d,%d,%d\n",index,timestamp.Month,timestamp.DayOfMonth,timestamp.Hour,timestamp.Min,timestamp.Sec,(float32)I1[ index],(float32)V1[ index]/1000,(float32)I1[ index]*V1[ index]/1000,(float32)I2[ index],(float32)V2[ index]/1000,(float32)I2[ index]*V2[ index]/1000,(float32)I3[ index],(float32)V3[ index]/1000,(float32)I3[ index]*V3[ index]/1000,(float32)I4[ index],(float32)V4[ index]/1000,(float32)I4[index]*V4[ index]/1000,(float32)Vbat[index]/1000,temperature,humidity,U_V[index],LW[index],MIR[index]);

    }

    else

    {

//        temperature = flash_dump.temp*0.0025177001953125 - 40;

        temperature = ((float32)flash_dump.temp)*0.0025177001953125 - 40.0;       

        humidity = flash_dump.humid*0.00152587890625;

        sprintf(disp, "\r%u ", sizeof(flash_dump)) ;                           /* No. 1 */

       

        snprintf(buf, 32, "%.5u, ", index) ;                                    /* No.2 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%ld, ",flash_dump.day_seq) ;                         /* No.3 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.I1) ;                   /* No.4 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.V1/1000) ;              /* No. 5 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.I1*flash_dump.V1/1000) ; /* No.6 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.I1) ;                    /* No.7 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.V1/1000) ;              /* No.8 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.I2*flash_dump.V2/1000) ; /* No.9 */

        strcat(disp, buf) ;       

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.I3) ;                    /* No.10 */

        strcat(disp, buf) ;      

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.V3/1000) ;               /* No.11 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.I3*flash_dump.V3/1000) ; /* No.12 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.I4) ;                    /* No.13 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.V4/1000) ;               /* No.14 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%5.2f,",(float32)flash_dump.I4*flash_dump.V4/1000) ; /* No.15 */

        strcat(disp, buf) ;       

        snprintf(buf, 32, "%5.2f, ",(float32)flash_dump.Vbat/1000) ;             /* No.16 */

        strcat(disp, buf) ;       

        snprintf(buf, 32, "%2.2f,",temperature) ;                               /* No.17 */

        strcat(disp, buf) ;       

        snprintf(buf, 32, "%2.2f,",humidity) ;                                  /* No.18 */

        strcat(disp, buf) ;

        snprintf(buf, 32, "%d,",flash_dump.U_V) ;                               /* No.19 */

        strcat(disp, buf) ;       

        snprintf(buf, 32, "%d,",flash_dump.LW) ;                                /* No.20 */

        strcat(disp, buf) ;       

        snprintf(buf, 32, "%d\n",flash_dump.MIR) ;                              /* No.21 */

        strcat(disp, buf) ;       

        len = strlen(disp) ;

/*

        len = sprintf(disp,

            "\r%u  // 1

            %.5u,  // 2

            %ld,   // 3

            %5.2f, // 4

            %5.2f, // 5

            %5.2f, // 6

            %5.2f, // 7

            %5.2f, // 8

            %5.2f, // 9

            %5.2f, // 10

            %5.2f, // 11

            %5.2f, // 12

            %5.2f, // 13

            %5.2f, // 14

            %5.2f, // 15

            %5.2f, // 16

            %2.2f, // 17

            %2.2f, // 18

            %d,    // 19

            %d,    // 20

            %d\n", // 21

            sizeof(flash_dump),                           // 1

            index,                                        // 2

            flash_dump.day_seq,                           // 3

            (float32)flash_dump.I1,                       // 4

            (float32)flash_dump.V1/1000,                  // 5

            (float32)flash_dump.I1*flash_dump.V1/1000,    // 6

            (float32)flash_dump.I1,                       // 7 (I2?)

            (float32)flash_dump.V1/1000,                  // 8 (V2?)

            (float32)flash_dump.I2*flash_dump.V2/1000,    // 9

            (float32)flash_dump.I3,                       // 10

            (float32)flash_dump.V3/1000,                  // 11

            (float32)flash_dump.I3*flash_dump.V3/1000,    // 12

            (float32)flash_dump.I4,                       // 13

            (float32)flash_dump.V4/1000,                  // 14

            (float32)flash_dump.I4*flash_dump.V4/1000,    // 15

            (float32)flash_dump.Vbat/1000,                // 16

            temperature,                                  // 17

            humidity,                                     // 18

            flash_dump.U_V,                               // 19

            flash_dump.LW,                                // 20

            flash_dump.MIR);                              // 21

*/

    }

   

    return len;

}   

==================

With this you can tell exactly which line is causing the problem.

Best Regards,

11-Mar-2020

Motoo Tanaka

Hi Motoo,

Wow. That's a lot of work I gave you. Appreciate your help. Sorry for making it complicated. I am trying the strcat now and I have increased the heap size to 0x1000. Just to understand the issue better, I will run my code with the new heap size, with %d and then with series of strcat. Sharing the results soon.

I am with strcat and the call trace is similar to previous.

0 appl1_start() ?????? ?????? 0x00000000 (All)

1 <signal handler called>() ?????? ?????? 0xFFFFFFF1 (All)

2 appl1_start() ?????? ?????? 0x00000000 (All)

3 <signal handler called>() ?????? ?????? 0xFFFFFFF9 (All)

4 __lshift() ?????? ?????? 0x0000FF90 (All)

5 _dtoa_r() ?????? ?????? 0x0000F880 (All)

6 __cvt() ?????? ?????? 0x0000E47E (All)

7 _printf_float() ?????? ?????? 0x0000E646 (All)

8 _svfprintf_r() ?????? ?????? 0x00010528 (All)

9 snprintf() ?????? ?????? 0x0000ED56 (All)

10 main() main.c 1650 0x0000344C (All)

1650          snprintf(buf, 32, "%5.2f,",(float32)V3[index]/1000) ;               /* No.11 */

Hi Motoo,

After replacing the %f with %d, I was getting garbage values for the global variable. After moving them to the main.c, issue is not seen. But still unable to resolve the original problem.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Dear Sajo-san,

> After replacing the %f with %d, I was getting garbage values for the global variable.

If this is happening in the "ISR", the global values must be defined as "volatile" to be accessed correctly. But I don't suggest you to use any print or memory handling function in it.

> After moving them to the main.c, issue is not seen.

This means the print statements are working OK, right?

> But still unable to resolve the original problem.

Does this mean you still get error in the debugger?

Is the error "exact" the same with the first question you post?

Or similar but showing something else?

Best Regards,

13-Mar-2020

Motoo Tanaka

MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

BTW,

> I am trying the strcat now and I have increased the heap size to 0x1000.

0x1000 for the heap may be too much, how about tryint to reduce it to 0x800 ~ 0x500?

moto

0 Likes

Hi Motoo,

I am now testing with the %d and no issues till now. I will post the

results by the end of the day.

On Fri, Mar 13, 2020 at 12:23 PM Motoo Tanaka <community-manager@cypress.com>

Hi Motoo, Len,

The problem was with the strcat. After using the first sprintf(disp,"S%.5u,", index) ; resolved the global variable issue. We can safely say that the root cause of the problem was the sprintf in ISR. After moving them to main.c and changing %f to %d resolved the stack overflow issue.

But I wonder why %f fails when the length of the sprintf is more i.e. 100+ bytes  even after increasing the heap size to even 0x2000. Main issue is certainly now with the stack or heap size but the %f function itself.

MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Dear Sajo-san,

Thank you for the good news!

To be honest I'm not believing in "%f", so that I usually I use "%d" instead.

Best Regards,

16-Mar-2020

Motoo Tanaka

0 Likes

SAJO,

I'm glad you've identified the issue.

%f processing in sprintf() does take more stack because it is making calls to the SW floating point library.

Len

Len
"Engineering is an Art. The Art of Compromise."
0 Likes