TMS320F2808: printf() format specifiers do not work, however they do work in sprintf().

Part Number: TMS320F2808

Tool/software:

The following code snippet...

    unsigned loop_count = 0;
    for (;;loop_count++)
    {
        static char scratch_buffer[40];
        printf("Hello from printf() %u!\n", loop_count);
        unsigned int length = sprintf(scratch_buffer, "Hello from sprintf() %u!\n", loop_count);
        HAL_UART_TX(&keypad_uart, (uint8_t*) scratch_buffer, length, HAL_ms_to_timer_counter(10000));

        stopwatch_delay(stopwatch_s_to_ticks(1));
    }
...produces the following output:
I.e. the format specifier %u doesn't work with printf(), but it does work with sprintf().
A few points:
  • Using CCS Version 20.2.0.12__1.8.0.
  • Simple app.  Pretty much just the above loop in main().
  • fputc() has been replaced to output stdout to SCI.
  • Stack size set to 0x400.
  • Heap size set to 0x800.
Are there any suggestions on how to fix this?
Thanks!
Bruce
  • Hi Bruce,

    We will get back to you on this.

    Best Regards,

    Aishwarya

  • Thanks Aishwarya,

    A few additional notes...

    • Not all format specifiers fail.  %s seems to work OK.  %d and %u don't.
    • Given that sprintf() seems to work OK, as a temporary quick-fix I'll create a printf_replacement() using sprintf() and use a compile time macro to replace instances of printf() with that. 

    Thanks again!

    Bruce

  • Hi Bruce,

    A couple things to check:

    1. Are you using one of the printf_support flags in your project? If not, can you try adding the printf_support=full option and see if it changes the behavior? You can check/add the flag by right clicking on the project and selecting Properties >>  Build >> C2000 Compiler >> Edit Flags.
    2. Also, can you check your .map file and see which function is being linked for printf to see which runtime lib file is being pulled in?

    Best Regards,

    Delaney

  • I'm trying to use 'nofloat'...

    When I select 'minimal', compile time errors result.

    Selecting 'full' has the same behavior.

    Here is the entry from the .map file when 'nofloat' is selected...

    .text      0    003f4000    0000330d     
                      003f4000    00000922     led_control.obj (.text)
                      003f4922    000006ce     processor_tasks.obj (.text)
                      003f4ff0    000005ca     rts2800_ml.lib : _printfi.c.obj (.text:__TI_printfi_nofloat)
                      003f55ba    0000030a     UART.obj (.text)
    

  • Hi Bruce,

    Can you show the compiler errors you get with printf_support=full? I believe this is the option you want to use for your %d and %u specifiers to work with printf().

    Best Regards,

    Delaney

  • Hello Delaney,

    Actually, I don't get compile errors when printf_support=full.  I was probably unclear about that.  The compile errors only occur when printf_support=minimal.

    The behavior when printf_support=full is the same as when printf_support=nofloat... the format specifiers are not expanded.

    Thanks!

    Bruce

  • Hi Bruce,

    I see, then the printf_support value doesn't sound like it is the issue here then. Let me try to replicate this behavior on my setup and get back to you in 1-2 days.

    Best Regards,

    Delaney

  • Hi Bruce,

    Apologies for the delay. I realized you're using the F2808x device, which is very old. I do not have access to hardware or software for this device unfortunately to test this out. 

    I tried testing this code on F28P65x with the same code you have provided and don't see the issue. Are you able to switch to a newer device? Also, which compiler version are you using that works for F2808x?

    Best Regards,

    Delaney

  • Hi Delany,

    Yes, the F2808 is very old.  However, it's too late in our design cycle to switch to something newer.

    We're using the latest version of CCS.  (20.2.0.12_1.80)   If you are asking if there was a version of compiler where printf() was working, I don't know.  This is the first time we've we've tried using printf().

    My guess is the problem with the F2808 is its limited RAM space.  The largest heap and stack we can allocate is 0x400 each.  Can you check the heap and stack size of the F28P65x project?  What happens if you set to 0x400?

    I believe printf() is crashing somewhere in the iostream layer.  Our uart_printf() implementation bypasses the stream layers and writes directly to the uart.  This seems to be an effective work around.  So, it's not completely necessary to get printf() working.

    Thanks!

    Bruce

  • I believe the compiler version we're using is TI v22.6.1.LTS.

  • Hi Bruce,

    Yes, let me check the heap and stack size with the F28P65x project and get back to you. Also, here is some other printf documentation for your reference: Tips for Using Printf

    Best Regards,

    Delaney

  • Hi Bruce,

    It looks like the stack size I'm using on the F28P65x is 0x3F8 and the heap size is only 0x200, so I don't believe that to be the issue. 

    I believe printf() is crashing somewhere in the iostream layer.  Our uart_printf() implementation bypasses the stream layers and writes directly to the uart.  This seems to be an effective work around.  So, it's not completely necessary to get printf() working.

    This may be your best approach as I can't reproduce the problem on my setup, so it's difficult to identify the reason for the behavior you're seeing. I will close this thread then but please feel free to make another if you have any other questions. 

    Best Regards,

    Delaney