Create timers for notification purposes

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
User avatar
XCHG
Member
Member
Posts: 416
Joined: Sat Nov 25, 2006 3:55 am
Location: Wisconsin
Contact:

Create timers for notification purposes

Post by XCHG »

What is the best way to create a timer that say, calls a procedure after a specific amount of time is passed. Should I be using the PIT or are there any other ways around this?
pcmattman
Member
Member
Posts: 2566
Joined: Sun Jan 14, 2007 9:15 pm
Libera.chat IRC: miselin
Location: Sydney, Australia (I come from a land down under!)
Contact:

Post by pcmattman »

Note that this idea is not tested...

I think the best way is to setup a callback system. An example is like this:

Code: Select all

int Seconds = 0;

void TimerCallback()
{
    printf( "Seconds passed: %d\n", Seconds++ );
}

void StartSecondCounter()
{
    SetTimerCallback( TimerCallback, 1000 ); // 1000 ms = 1 s
}
Then, you have to keep a linked list of every callback function:

Code: Select all

typedef struct TimerCallbackEntry {
    long timeToWait;
    long myCounter;
    void (*CallbackFunction)();
    TimerCallbackEntry* nextEnt;
}
Whenever the timer fires, each list's counter gets incremeted. With a bit of modulus arithmetic:

Code: Select all

if( tmp->myCounter % tmp->timeToWait == 0 )
    tmp->CallbackFunction();
Of course, I'll leave the initialization up to you. If you're using ASM, that's a totally different matter, I'm afraid. Either way, I hope this helps someone.
User avatar
XCHG
Member
Member
Posts: 416
Joined: Sat Nov 25, 2006 3:55 am
Location: Wisconsin
Contact:

Post by XCHG »

So I should be using System's timer on IRQ0 as a scheduler right? I should be fiddling with PIT eh? I can then set the number of milliseconds between each IRQ and then put a simple scheduler in IRQ0 handler procedure.
User avatar
Brendan
Member
Member
Posts: 8561
Joined: Sat Jan 15, 2005 12:00 am
Location: At his keyboard!
Contact:

Post by Brendan »

Hi,
XCHG wrote:So I should be using System's timer on IRQ0 as a scheduler right? I should be fiddling with PIT eh? I can then set the number of milliseconds between each IRQ and then put a simple scheduler in IRQ0 handler procedure.
I wouldn't quite phrase it like that ("IRQ0 as a scheduler" - it makes it sound like the timer IRQ handler is the scheduler).

For most systems, most task switches are caused by the currently running task blocking or a higher priority task unblocking, and aren't caused by a task using all of the time it's given. Some tasks are "CPU bound", but not all.

When writing a scheduler, I'd recommend doing it in stages. First write a "switch to task X" function (to eventually be used when a higher priority task unblocks), then write a "find the best task to switch to and switch to it" function (to eventually be used when the currently running task blocks). The timer IRQ just calls the "find the best task to switch to" function if the time given to the task expires.

As for which timer, use some abstraction so it doesn't matter which timer - you'll be better off in the long run. In 5 years time you might decide to support SMP and want to use local APIC timers instead, or in 3 years time you might want to support HPET timers. With some sort of abstraction layer the scheduler doesn't need to care which timer it's actually using, and you could detect which timer to use (based on what is present) instead of hard-coding it.


Cheers,

Brendan
For all things; perfection is, and will always remain, impossible to achieve in practice. However; by striving for perfection we create things that are as perfect as practically possible. Let the pursuit of perfection be our guide.
User avatar
XCHG
Member
Member
Posts: 416
Joined: Sat Nov 25, 2006 3:55 am
Location: Wisconsin
Contact:

Post by XCHG »

Okay that's great. Thank you both for answering my question. Appreciations. I fiddled around with some initialization routines of the 8254 PIT today and got a better understanding of how it should be used. Hope I can create a simple scheduler soon.
Post Reply