clinuxtimerpthreadsintervals

Implementing timed events in C


I am writing a simple application to check some records in an interval on Linux (x86/x86_64). Each record has its own checking interval which can be between 5 and 300 seconds. This is the record structure:

typedef struct record_t {
    char name[256];
    time_t last_check;
    unsigned int interval;
    unsigned long amount;
    struct record_t *next;
} struct_t;

And the thread that checks records:

/* 'records' is a pointer to the first record in the linked list */
while(1) 
{
    for (current_record = records;
         current_record != NULL;
         current_record = current_record->next)
    {
        if(current_record->last_check + current_record->interval < time(0))
            update_record(current_record);
    }

    sleep(1);
}

The record list's length can be vary greatly (e.g., from 2 to 100 000). And this will get slower and slower with each element pushed in the list... Is there a way to optimize it or have a trigger with each record so instead of checking everything with a loop, a callback is invoked when the interval passes?

More or less, I'm looking for something like setInterval() from JavaScript.


Solution

  • Implement a timer wheel. Make an array of 301 pointers. Instead of queuing the records just like that, queue them according to the time-out.

    Have:

    while(1) {
        sleep (1);
        currIndx = (currIndx + 1) % 301;
    
        /* Process the link list starting at that variable. */
        procQ = timerWheel[currIndx];
    
        /* Requeue if necessary */
    
    }
    

    And the queuing code:

    queIndx = (currIndx + timeout) % 301;
    procQ = timerWheel[queIndx];
    /* Add at the head of the linked list */