Wednesday, March 18, 2009

QTimer and no monotonic clock support

I found myself dealing with qt-embedded and QTimers again. There's a board whose software configuration doesn't support monotonic clocks so changing the date back in time causes running QTimer's to cease activity.

I chose to patch qt-embedded 4.5.0. The fix is simple, I just had replace this function in src/corelib/kernel/qeventdispatcher_unix.cpp



void QTimerInfoList::registerTimer(int timerId, int interval, QObject *object)
{
QTimerInfo *t = new QTimerInfo;
t->id = timerId;
t->interval.tv_sec = interval / 1000;
t->interval.tv_usec = (interval % 1000) * 1000;
t->timeout = updateCurrentTime() + t->interval;
t->obj = object;
t->inTimerEvent = false;

timerInsert(t);
}

by this one:



void QTimerInfoList::registerTimer(int timerId, int interval, QObject *object)
{
/** add this 2 lines */
updateCurrentTime();
repairTimersIfNeeded();

QTimerInfo *t = new QTimerInfo;
t->id = timerId;
t->interval.tv_sec = interval / 1000;
t->interval.tv_usec = (interval % 1000) * 1000;
t->timeout = updateCurrentTime() + t->interval;
t->obj = object;
t->inTimerEvent = false;

timerInsert(t);
}

After that qt-embedded should be recompiled (a full recompilation isn't needed, the only file that needs to be compiled again is the one modified, and then a full relink and install; make will do the job).

What happens is that everytime a timer is registered, Qt will update the current time and try to fix the timers if it's needed. This will make newly registered timers work after the date is changed backwards, but old timers won't run properly. I created a class which tracks the QTimers present in the application so that it is able to stop and start them again. This is not the best solution but I had to do a quick fix on this and it works.

No comments:

Post a Comment