wvtimestream.cc

00001 /*
00002  * Worldvisions Weaver Software:
00003  *   Copyright (C) 1997-2002 Net Integration Technologies, Inc.
00004  *
00005  * See wvtimestream.h.
00006  */
00007 #include "wvtimestream.h"
00008 
00009 WvTimeStream::WvTimeStream():
00010     last(wvtime_zero), next(wvtime_zero), ms_per_tick(0)
00011 {
00012 }
00013 
00014 
00015 void WvTimeStream::set_timer(time_t msec)
00016 {
00017     WvTime now = wvtime();
00018 
00019     ms_per_tick = msec > 0 ? msec : 0;
00020     next = msecadd(now, ms_per_tick);
00021     last = now;
00022 }
00023 
00024 
00025 bool WvTimeStream::isok() const
00026 {
00027     return true;
00028 }
00029 
00030 
00031 bool WvTimeStream::pre_select(SelectInfo &si)
00032 {
00033     WvTime now;
00034     time_t diff;
00035     bool ready = WvStream::pre_select(si);
00036     
00037     //fprintf(stderr, "%p: timestream pre_select ready=%d mspt=%ld msto=%ld\n",
00038     //     this, ready, ms_per_tick, si.msec_timeout);
00039 
00040     if (ms_per_tick)
00041     {
00042         now = wvtime();
00043         
00044         /* Are we going back in time? If so, adjust the due time. */
00045         if (now < last)
00046             next = tvdiff(next, tvdiff(last, now));
00047         
00048         last = now;
00049 
00050         if (next < now || next == now)
00051         {
00052             si.msec_timeout = 0;
00053             return true;
00054         }
00055 
00056         diff = msecdiff(next, now);
00057         diff = diff < 0 ? 0 : diff;
00058         if (diff < si.msec_timeout || si.msec_timeout < 0)
00059             si.msec_timeout = diff;
00060     }
00061 
00062     return ready;
00063 }
00064 
00065 
00066 bool WvTimeStream::post_select(SelectInfo &si)
00067 {
00068     WvTime now = wvtime();
00069 
00070     return WvStream::post_select(si) || (ms_per_tick && next < now);
00071 }
00072 
00073 
00074 void WvTimeStream::execute()
00075 {
00076     WvStream::execute();
00077 
00078     /* Schedule our next timer event, unless alarm_is_ticking, which
00079      * would mean that we're here because someone used alarm() rather
00080      * than because our timer expired. */
00081     if (!alarm_was_ticking)
00082     {
00083         WvTime now = wvtime();
00084 
00085         next = msecadd(next, ms_per_tick);
00086         
00087         if (msecdiff(next, now) > ms_per_tick * 100
00088                 || msecdiff(now, next) > ms_per_tick * 100)
00089         {
00090             // reset if we fall forward or behind WAY too excessively
00091             // This is usually due to a change in system time
00092             last = now;
00093             next = msecadd(last, ms_per_tick);
00094         }
00095         else if (msecdiff(next, now) > ms_per_tick * 10)
00096             // compensate if we fall behind too excessively
00097             next = msecadd(now, ms_per_tick);
00098     }
00099 }

Generated on Mon Feb 5 10:54:30 2007 for WvStreams by  doxygen 1.5.1