performance: switch statements, ldap and waiteu

Technical questions regarding the XTC tools and programming with XMOS.
Post Reply
jmtaylor
Member
Posts: 15
Joined: Tue Aug 20, 2013 10:01 am

performance: switch statements, ldap and waiteu

Post by jmtaylor »

I have some moderately complex code that monitors a whole load of events simultaneously (timers, pin inputs, etc) and performs actions for each input. This is written in C code based around one big select statement.

Looking at the disassembly, I see that every time an event fires, my correct event handler is called but then there is a huge long bit of code to set up all the events again (calls to ldap, ldw and so on) before a call to waiteu. My understanding from reading up on these instructions is that in principle there should not be any need to go through all the hassle of setting up the events again - it should be possible just to call waiteu again. If this was the case with my code, it would make it a lot more responsive - currently the majority of time is spent configuring events again after each event that fires.

Am I correct that all the ldap etc is not in principle required to be repeated each time? If so, is there anything I could do to help xtimecomposer realise this and generate more efficient assembly code? i.e. just doing all that once at start of day and then not having to do it every time?

This apparent inefficiency occurs even if I write a much simpler select statement that does not involve any calls through to other functions, which makes me think that the compiler just insists on doing all the event setup every time - but, as I say, it seems from my reading of the docs that that is unnecessary...

Thanks for any suggestions.


henk
Respected Member
Posts: 347
Joined: Wed Jan 27, 2016 5:21 pm

Post by henk »

Hi jmtaylor,

Yes - you are completely right. There are lots of optimisations that could be performed for the special case

Code: Select all

while(condition) select { case case case };
There are various reasons why the compiler does not do this at present; it needs a fair amount of analysis to do the general case, and it could just do it on some special cases but that would be quite a fickle process where one small change to your code makes it less efficient.

Where it matters, I have written those select statements in assembly code.
The normal assembly structure would be as follows:

Code: Select all

   clre

// For each resource:
   setv       // set up at least setv,
   setc       // possibly setc, setd, and setev
   setd
   setev
   eeu        // and almost always eeu (enable)

// Now enter the select, dispatch the first event
   waiteu

// For each case, you need a piece of code that at least performs an in
label_first_case:
    in

            // add all code here to do data/control for the case
            // This may include any of the following

    setd    // change the data for this particular case,
            // e.g. from 0 to 1, or a new time
    setc    // change the condition for this particular case,
            // e.g. from EQ to NEQ
    eeu/edu // enable or disable any of the cases.
            // This implements the guards in the case
            // For example, if the buffer is no longer
            // full you can enable the case that fills it

             // You can choose one of two endings, either a waiteu
             // or a waitt/waitf with the condition followed by a branch
    waiteu   // while(1): unconditional dispatch of next event
    waitt  c // while(c): dispatch next event if condition is still true
    bu statement-after-loop  // and if condition fails, bail out.
Keep in mind, a waiteu instruction is final; it will go somewhere else. So it implements both the branch back and the select in one fell swoop.

Hope this helps,
Henk
jmtaylor
Member
Posts: 15
Joined: Tue Aug 20, 2013 10:01 am

Post by jmtaylor »

(Very) belated thanks for your reply, Henk. (I had thought I would be notified by email if a reply appeared, but apparently not)

Anyway, thankyou for replying and for confirming that you wouldn't expect the compiler to optimize. It's helpful to know that there is nothing much I can do at the level of the C code to improve performance. I'm not in any great hurry to start writing assembly by hand just now, but it's good to know that the option is there. I'll keep an eye on performance and bear it in mind as the next step.

Cheers
Jonny.
Post Reply