8 years, 5 months ago.

wait vs for-loop?

I noticed that you have replaced the wait() by for-loops. The publish comment suggest that you want to avoid blocking code. However, if you check the wait() implementation in mbed-src you will see that wait() is implemented as a while-loop that just tests the us_ticker:

void wait_us(int us) {
    uint32_t start = us_ticker_read();
    while ((us_ticker_read() - start) < (uint32_t)us);
}

So effectively wait() can be interrupted. Also note that for-loops are very much clockspeed dependant and your code may not run on faster mbeds..

Question relating to:

TextLCD library for controlling various LCD panels based on the HD44780 4-bit interface (does not contain blocking code) HD44780, TextLCD

1 Answer

8 years, 5 months ago.

I was developing an energymeter code which required TextLCD library functions to be called inside an ISR. I was facing problems like the interrupt wont get called more than once or sometimes the mbed would freeze after that one call. In the Handbook page of Ticker class: https://developer.mbed.org/handbook/Ticker, I found a warning which said not to use calls to wait, infinite loops or blocking code in general. As the only blocking code I could find was the wait inside the TextLCD routines, I tried replacing those with loops just to check, and it worked. I am aware of the limitations and/or inefficiency of using loops like these but I was on a timeline and as my specific requirement was met I didn't bother much!

And in the implementation of wait I see a while loop (though its not infinitive), but my guess would be this is what actually causes the problems when using with Ticker objects.

Any more efficient way of solving this?

It is not a good idea to use waits or blocking code or long loops inside an ISR. The reason is that new interrupts are not handled while you are still busy working on the previous one. So a long delay in the interrupt handler (wait or loop doesnt matter) would be a problem and could cause the processor to freeze. Perhaps the loops are just a bit faster than the original wait and therefore it happens to work in your case. The system would be instable again when the interrupts happen faster or when you display more text in the ISR.

In general is would be best to just set some flag in the interrupt and return. Do the actual display update in a while loop in your main that checks flags to see what needs to be done.

posted by Wim Huiskamp 03 Nov 2015