I'm going to preface this posting with the assurance that I believe
something is setup incorrectly on my system. Any help in finding out what
that something is would be greatly appreciated.
Every now and again I get a glitch of 1.0 -> 1.5 ms in my real time
processes. I've compiled a ridiculously simple example below, to
illustrate my problem. The following code uses clock_gethrtime to grab two
consecutive times from the CLOCK_REALTIME clock, periodically. If the time
between the two clock grabs is a new maximum, it is recorded.
A typical dmesg looks as follows:
Delay of 192ns near 0ms
Delay of 288ns near 95ms
Delay of 352ns near 1609ms
Delay of 384ns near 1648ms
Delay of 448ns near 23322ms
Delay of 1141792ns near 937517ms
Delay of 1224000ns near 1530446ms
You see the two vastly different scales. The first 5 maximum delays are
under .5 useconds, and don't hurt me. The final 2 maximum delays however,
are larger than a single cycle period (1000000 ns). Any advice?
-Chuck
// Stipped down DAQ code - Chuck
// ***** System headers ***** //
#include <rtl.h>
#include <rtl_sync.h>
#include <time.h>
#include <pthread.h>
// ***** System Definitions ***** //
#define FREQUENCY 1000 // Thread frequency [=] Hz
// ***** Function Declarations ***** //
void *daq_code(void*); // DAQ Periodic function
// ***** Global Variables ***** //
pthread_t daq_thread; // main rtlinux thread
// Simple thread measures clock
void *daq_code(void *param)
{
rtl_irqstate_t irqstate;
hrtime_t zero_time, tick_time, tock_time;
long delay_time, delay, max_delay=0;
zero_time = clock_gethrtime(CLOCK_REALTIME);
while (1) // periodic task, must loop
{
// Begin DANGER
rtl_no_interrupts(irqstate);
tick_time = clock_gethrtime(CLOCK_REALTIME);
tock_time = clock_gethrtime(CLOCK_REALTIME);
delay = (long)(tock_time - tick_time);
rtl_restore_interrupts(irqstate);
// End DANGER
if (delay > max_delay)
{
// reset delay max
max_delay = delay;
// reset time of max, >>20 is ~equal to /1e6
delay_time = (long)((tock_time - zero_time)>>20);
printk( "Delay of %7ldns near %7ldms\n", max_delay, delay_time);
}
pthread_wait_np( );
}
}
// ***** Module Standard Functions ***** ///
int init_module(void)
{
pthread_attr_t attr;
struct sched_param sched_param;
hrtime_t period, soon;
// initialize pthread attributes
if( pthread_attr_init(&attr) )
printk( "Cannot initialize pthread attributes\n" );
// modify pthread priority
sched_param.sched_priority = 1;
if ( pthread_attr_setschedparam (&attr, &sched_param) )
printk( "Cannot set pthread priority: 0\n" );
// initialize the main thread
if( pthread_create (&daq_thread, &attr, daq_code,(void *)1) )
printk( "Cannot create pthread\n" );
// make the thread run off the CPU clock
period = HRTICKS_PER_SEC / FREQUENCY;
soon = clock_gethrtime(CLOCK_REALTIME) + (100 * period);
if( pthread_make_periodic_np (daq_thread, soon, period) )
printk( "Cannot make pthread periodic\n" );
return 0;
}
void cleanup_module(void)
{
// destroy periodic thread
if( pthread_delete_np(daq_thread) )
printk( "Cannot destroy phread\n" );
}
-- [rtl] ---
To unsubscribe:
echo "unsubscribe rtl" | mail [EMAIL PROTECTED] OR
echo "unsubscribe rtl <Your_email>" | mail [EMAIL PROTECTED]
---
For more information on Real-Time Linux see:
http://www.rtlinux.org/rtlinux/