This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

TMS320F28388D: F28388DPTPS: Possible compiler restriction

Part Number: TMS320F28388D
Other Parts Discussed in Thread: SYSCONFIG, C2000WARE,

Hi Experts,

I am posting this on behalf of the customer. Here it is below.

I am trying to read and then average a ADC value on the CLA, then pass the averaged value though a shared CLA/CPU variable to the CPU. I will share in a moment how i declared the variables in the .c, .cla, and shared.h.

but first; the compilation issue i get is when I try to average the new ADC value

tempDouble = HWREGH(ADCCRESULT_BASE + 0x0U + lastRRPointer_s);
tempDouble = (0.1 * tempDouble) + (C28CLA_secondary.AC target="_blank">secondary.AC2DCMON * 0.9);
C28CLA_secondary.AC2DCMON = tempDouble;

give the compilation error: error #99923: "../CLA1.cla", line 352: CLA does not permit function calls in background tasks. Try inlining function.

the compilation error claims that it is occuring on line 352 (the first line of code with the HWREGH macro) and by the way - this error only shows up when the last line is present - if its just the first 2 lines of code then there is no compilation error

Here is my variable declaration code in case it helps;

main.c is;

#ifdef __cplusplus
#pragma DATA_SECTION("CLADataLS0")
#else
#pragma DATA_SECTION(C28CLA_secondary,"CLADataLS0")
#endif //__cplusplus
struct C28CLA_secondary_struct C28CLA_secondary; //Secondary signals coming from the CLA. These signals are grouped together as "secondary" given their less than high speed nature. This group represents signals updated at a about the emission loop speed.

shared.h is;

struct C28CLA_secondary_struct {
volatile double AC1DCMON;
volatile double AC2DCMON;
} extern C28CLA_secondary;

well and actually nothing in the .cla (because its declared in the .h. I hope that is correct lol)

I am not using a function call.

 

I was using Ti’s function MACRO for access hardware registers. HOWEVER – even If I remove the MACRO-FUNCTION call for accessing hardware registers, and replace that code with a hard coded value, then I still get the same compilation error.

 

The original line of code; (HWREGH is a macro-function)

C28CLA_secondary.AC1DCMON = (0.9 * C28CLA_secondary.AC1DCMON) + (0.1 * HWREGH(ADCCRESULT_BASE + 0x0U + lastRRPointer_s));

 

Code with macro-function removed and it still gives compilation error

C28CLA_secondary.AC1DCMON = (0.9 * C28CLA_secondary.AC1DCMON) + (0.1 * 123);

Thank you in advance!

Best regards,

Jonathan

  • Hello,

    I have brought this thread to the attention of the compiler experts. Please note that due to the local holiday there, you will likely not hear a response until tomorrow.

    Thanks

    ki

  • Please put things into the state where this occurs ...

    error #99923: "../CLA1.cla", line 352: CLA does not permit function calls in background tasks. Try inlining function.

    For the file CLA1.cla, please follow the directions in the article How to Submit a Compiler Test Case.

    Thanks and regards,

    -George

  • Hi George,

    Thank you for your help. I have generated and attached the PP files as per "How to Submit a Compiler Test Case". I have also simplified the code to help focus our troubleshooting efforts. I will include these files too. 

    The files are mostly empty. Here is how I declared the variables;

    Global declaration in main_CPU1.c

    #pragma DATA_SECTION(C28CLA_secondary,"CLADataLS0")
    struct C28CLA_secondary_struct C28CLA_secondary;

    Definition of the struct in the shared header file between the C28 and CLA in CPU1_CLA1_shared.h

    struct C28CLA_secondary_struct {
    volatile double AC1DCMON;
    volatile double AC2DCMON;
    } extern C28CLA_secondary;

    Compilation error occurs on the single line of code inside the BG Task in CLA1.cla

    __attribute__((interrupt("background"))) void Cla1BackgroundTask ( void )
    {
        C28CLA_secondary.AC2DCMON = (0.9 * C28CLA_secondary.AC2DCMON);
    }

    This project is based off of the CLA BG TASK example project. Please let me know if you need more info (like sysconfig etc.). I hope this write up was helpful.

    I am having trouble uploading the .PP files. I might post this and then try to attach the .PP files to a reply to this post. Sorry,

  • Here are the .PP files. For some reason I had to change the file type to ".c" to be able to upload them, but I promise they are actually the ".PP" files!

    CLA1.c6457.main_CPU1.c

  • I also just want to mention that you could change the variable type from a struct to something simpler - like an uint16_t or uint32_t - and you will get the same results.

  • Thank you for the test case.  Unfortunately, I cannot reproduce ...

    error #99923: "../CLA1.cla", line 352: CLA does not permit function calls in background tasks. Try inlining function.

    Please supply the version of the compiler, and all the build options, exactly as the compiler sees them.  Copy and paste the text, and do not use a screen shot.

    Are you sure you sent the correct code?  I search the files for ...

    tempDouble = HWREGH(ADCCRESULT_BASE + 0x0U + lastRRPointer_s);
    tempDouble = (0.1 * tempDouble) + (C28CLA_secondary.AC target="_blank">secondary.AC2DCMON * 0.9);
    C28CLA_secondary.AC2DCMON = tempDouble;

    I don't see that.

    Thanks and regards,

    -George

  • Hi George,

    Could you work off of my reply post instead of the original post? In the reply post, I took the time to format it nicely and clean up the code for your convenience!

    I deleted every irrelevant line of code in the project so that there was only the shared variable declaration, the sysconfig generated code, and the single assignment statement inside the BG TASK that gives the compiler error.

    Compiler version:

    C2000 TI V22.6.0.LTS

    Build Options:


    **** Build of configuration CPU1_FLASH for project SHV_Controller_Base ****

    "C:\\ti\\ccs1230\\ccs\\utils\\bin\\gmake" -k -j 16 all -O

    Building file: "../CLA1.cla"
    Invoking: C2000 Compiler
    "C:/ti/ccs1230/ccs/tools/compiler/ti-cgt-c2000_22.6.0.LTS/bin/cl2000" -v28 -ml -mt --cla_support=cla2 --float_support=fpu64 --idiv_support=idiv0 --tmu_support=tmu0 --vcu_support=vcrc -O0 --include_path="C:/Users/bschiller/TI TEST VERSION/SHV_Controller_Base" --include_path="C:/ti/C2000Ware_4_03_00_00" --include_path="C:/Users/bschiller/TI TEST VERSION/SHV_Controller_Base/device" --include_path="C:/ti/C2000Ware_4_03_00_00/driverlib/f2838x/driverlib" --include_path="C:/ti/ccs1230/ccs/tools/compiler/ti-cgt-c2000_22.6.0.LTS/include" --define=_FLASH --define=CPU1 --preproc_with_comment --preproc_with_compile --diag_suppress=10063 --diag_warning=225 --diag_wrap=off --display_error_number --gen_func_subsections=on --abi=eabi --cla_background_task=on --cla_signed_compare_workaround=on --include_path="C:/Users/bschiller/TI TEST VERSION/SHV_Controller_Base/CPU1_FLASH/syscfg" --cmd_file="syscfg/board.opt" --cmd_file="syscfg/c2000ware_libraries.opt" "../CLA1.cla"
    "../CLA1.cla", line 134: advice #30012: (Performance) Double-precision float multiplication operation was not eliminated during optimization. Using inefficient fallback; consider modifying code to not require this operation.
    error #99923: "../CLA1.cla", line 134: CLA does not permit function calls in background tasks. Try inlining function.


    >> Compilation failure
    subdir_rules.mk:9: recipe for target 'CLA1.obj' failed
    gmake: *** [CLA1.obj] Error 1
    gmake: Target 'all' not remade because of errors.

    **** Build Finished ****

    I hope this helps!

  • I understand the problem now.  A background task cannot call any functions.  What about an expression like ...

    C28CLA_secondary.AC2DCMON = (0.9 * C28CLA_secondary.AC2DCMON);

    It has no explicit function call.  But that double precision multiply cannot be computed with instructions on the CLA.  Thus, it is implemented by calling a function from the compiler RTS library which computes it.  This implicit function call is what causes ...

    error #99923: "../CLA1.cla", line 134: CLA does not permit function calls in background tasks. Try inlining function.

    ... to be emitted.  In this case, inlining is not a solution.  You have to somehow change the code so no double precision operations are required.  Something like ...

    float_variable1 = 0.9f * float_variable2;

    ... is fine.  Note the f suffix on the constant 0.9f.

    Unfortunately, I cannot give specific advice on how to change your code.  I don't understand it well enough.

    Thanks and regards,

    -George

  • Thank you, George!

    That makes sense given the hardware differences between the C28 and CLA on my TMS320F28388D - but could you help me understand why it matters if the double-precision variable used is local or shared between the C28/CLA? (maybe if I better understood the difference here I could figure out a work-around)

    For example, If I use double-precision variables that are declared inside the BGTASK then I can compile;

    double_local_variable1 = 0.9f * double_local_variable2;

    but If I use a shared double-precision variable (like what I shared before - declared in main and extern to CLA) then the compiler uses an non-inline function call?

    Thank you for your help - I'm not ready to give up double precision yet, unless I have too!

  • I'm not certain, but I suspect when you ...

    use double-precision variables that are declared inside the BGTASK then I can compile;

    double_local_variable1 = 0.9f * double_local_variable2;

    ... that code is optimized away.  Build with no optimization, or make those variables volatile, and I suspect ...

    error #99923: "../CLA1.cla", line 134: CLA does not permit function calls in background tasks. Try inlining function.

    ... happens again.

    Thanks and regards,

    -George

  • George you are correct, once again! - it was being optimized out and that was why it was not giving the error.

    Ok; last question, I swear!

    I am ready to use floats instead of doubles - but I still get the same error (99923) when I use floats. Am I still missing something?

    I am using a TMS320f28388D. This is the code in my background task - the rest of the project is identical to what I shared previously. The error (99923) is given for the line "test = 1.1 * test;".

        volatile float test = 0;
        test  = 1.1 * test;

    Thank you for helping us understand what is going on,

    Brent

  • The default type of a constant like 1.1 is double.  If one part of an expression is double, it causes the entire expression to be computed as double.  To change the type of a constant to float, add the f suffx and write it 1.1f.

    Thanks and regards,

    -George

  • OK OK - that's the last time you get to make me look dumb! (at least in this thread! Stuck out tongue)

    Thank you for all your help, George. Slight smile

    Cheers, 

    Brent