Embedded linux and achievable timer rate

I've been stopped dead by a limitation with the ARM-9 250 MHz SBCs, running Linux, that I've been relying on for my next project. The maximum rate I can run a repeat timer (setitimer, etc) at is 50Hz, ie. 20000 uS repeat time. If I set the repeat rate any faster the thing still repeats every 20mS. Is this a standard 'feature' of Linux SBCs? Does anyone run an SBC that will do significantly better, without torching the Linux OS? (I'm looking for

10mS).
Reply to
Bruce Varley
Loading thread data ...

I believe the Linux kernel discipline is built around an assumption of

100Hz "preemption rate".

You may need to carve out your own hardware timer and have it generate events, or hit a callback. Or there's this:

formatting link

There's example code for a kernel space timer - but it may well be up against the same limitation. I haven't tried it...

it *is* kernel space, so use your plus-4 Linux wizard's hat and all that.

--
Les Cargill
Reply to
Les Cargill

There are a variety of timing sources within Linux. setitimer may be limited, but if you want to do a bit more work to roll your own using some higher resolution resource you should be able to get there. Depending on the nature of your device you may find some gaps while some interrupt or other takes all the time (yada yada about "hard real time"), but you should be able to get far better performance (

Reply to
Frank Miles

Good to know - I never actually had to dive into it.

--
Les Cargill
Reply to
Les Cargill

Maybe. There?s a build-time configuration parameter, CONFIG_HZ. In menuconfig, it can be found at Processor Type and Features / Timer Frequency. On my amd64 it has options to be set to 100, 250, 300, or

1000. See if that?s set incorrectly for your application before going and wading into the code!

Chris

Reply to
Christopher Head

The native 10ms ticking rate can be achieved with the select() system call, which can be used as a fairly portable way to sleep. For some reason, all other system calls (setitimer(), nanosleep(), etc.) seem to be unable to bl ock for less than two clock ticks (20 milliseconds).

When using select() in Linux, the timeout value passed to select() is round ed up to the nearest tick (10 milliseconds on desktop POSIX). The timeout c annot be too short, because the system might choose to busy-wait for very s hort timeouts. Also according to the man pages, the function select() on P OSIX modifies the timeout argument to reflect the amount of time not slept. Most other implementations do not do this. This quirk is handled in a port able way by always setting the microsecond part of the structure before each select() c all:

struct timeval timeout = { 0 }; . . . while (1) { // do timed processing at 10ms interval... timeout.tv_usec = 10000UL; /* set the desired tick interval */ select(0, 0, 0, 0, &timeout); /* sleep for the full tick */ }

Miro Samek state-machine.com

Reply to
Miro Samek

ElectronDepot website is not affiliated with any of the manufacturers or service providers discussed here. All logos and trade names are the property of their respective owners.