home *** CD-ROM | disk | FTP | other *** search
/ PC World Komputer 1999 mARCH / PCWK3A99.iso / Linux / DDD331 / DDD-3_1_.000 / DDD-3_1_ / ddd-3.1.1 / ddd / TimeOut.C < prev    next >
C/C++ Source or Header  |  1998-04-16  |  6KB  |  203 lines

  1. // $Id: TimeOut.C,v 1.10 1998/04/16 13:49:23 zeller Exp $ -*- C++ -*-
  2. // Xt TimeOut debugging routines
  3.  
  4. // Copyright (C) 1997 Technische Universitaet Braunschweig, Germany.
  5. // Written by Andreas Zeller <zeller@ips.cs.tu-bs.de>.
  6. // 
  7. // This file is part of DDD.
  8. // 
  9. // DDD is free software; you can redistribute it and/or
  10. // modify it under the terms of the GNU General Public
  11. // License as published by the Free Software Foundation; either
  12. // version 2 of the License, or (at your option) any later version.
  13. // 
  14. // DDD is distributed in the hope that it will be useful,
  15. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  16. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  17. // See the GNU General Public License for more details.
  18. // 
  19. // You should have received a copy of the GNU General Public
  20. // License along with DDD -- see the file COPYING.
  21. // If not, write to the Free Software Foundation, Inc.,
  22. // 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
  23. // 
  24. // DDD is the data display debugger.
  25. // For details, see the DDD World-Wide-Web page, 
  26. // `http://www.cs.tu-bs.de/softech/ddd/',
  27. // or send a mail to the DDD developers <ddd@ips.cs.tu-bs.de>.
  28.  
  29. char TimeOut_rcsid[] = 
  30.     "$Id: TimeOut.C,v 1.10 1998/04/16 13:49:23 zeller Exp $";
  31.  
  32. #ifdef __GNUG__
  33. #pragma implementation
  34. #endif
  35.  
  36. #include "TimeOut.h"
  37. #include "strclass.h"
  38. #include "assert.h"
  39. #include "bool.h"
  40.  
  41. #include <iostream.h>
  42. #include <stdlib.h>        // abort()
  43.  
  44. #undef XtAppAddTimeOut
  45. #undef XtRemoveTimeOut
  46.  
  47. // Set this to 1 to log all timer actions
  48. #define LOG_TIMERS 0
  49.  
  50. struct TimerInfo {
  51.     XtIntervalId timer;        // The id as received from XtAppAddTimeOut()
  52.     XtIntervalId tic;        // The unique id we use instead
  53.     unsigned long interval;    // INTERVAL arg given to XtAppAddTimeOut()
  54.     XtTimerCallbackProc proc;   // PROC     arg given to XtAppAddTimeOut()
  55.     XtPointer closure;        // CLOSURE  arg given to XtAppAddTimeOut()
  56.     string file;        // The file where XtAppAddTimeOut() was called
  57.     int line;            // The line where XtAppAddTimeOut() was called
  58.     TimerInfo *next;        // Next pending timer
  59.  
  60.     TimerInfo()
  61.     : timer(0), tic(0), interval(0), proc(0), closure(0), file(), line(0),
  62.       next(0)
  63.     {}
  64.  
  65. private:
  66.     TimerInfo(const TimerInfo&)
  67.     : timer(0), tic(0), interval(0), proc(0), closure(0), file(), line(0),
  68.       next(0)
  69.     {
  70.     assert(0);
  71.     }
  72.  
  73.     TimerInfo& operator = (const TimerInfo&)
  74.     {
  75.     assert(0); return *this;
  76.     }
  77. };
  78.  
  79. // List of pending timers
  80. static TimerInfo *pending_timers = 0;
  81.  
  82. // Counter
  83. static XtIntervalId timer_tics = 0;
  84.  
  85. // Return number of pending timers (i.e. not yet called)
  86. int MyPendingTimeOuts()
  87. {
  88.     int count = 0;
  89.     for (TimerInfo *ti = pending_timers; ti != 0; ti = ti->next)
  90.     count++;
  91.  
  92.     return count;
  93. }
  94.  
  95. // When timer is called, remove TimerInfo from list
  96. static void MyTimerProc(XtPointer client_data, XtIntervalId *)
  97. {
  98.     TimerInfo *tm = (TimerInfo *)client_data;
  99.  
  100.     // Remove from pending list
  101.     bool removed = false;
  102.     TimerInfo *tp = 0;
  103.     for (TimerInfo *ti = pending_timers; ti != 0; tp = ti, ti = ti->next)
  104.     {
  105.     if (ti == tm)
  106.     {
  107.         if (tp != 0)
  108.         tp->next = ti->next;
  109.         else
  110.         pending_timers = ti->next;
  111.  
  112.         removed = true;
  113.         break;
  114.     }
  115.     }
  116.  
  117.     assert(removed);
  118.     if (!removed)        // Just use it
  119.     abort();
  120.  
  121. #if LOG_TIMERS
  122.     clog << "TimeOut: " << tm->file << ":" << tm->line << ": timer " 
  123.      << tm->tic << " (" << XtPointer(tm->timer) << ")"
  124.      << " expired (" << MyPendingTimeOuts() << " still pending)\n";
  125. #endif
  126.  
  127.     tm->proc(tm->closure, &tm->tic);
  128.  
  129.     delete tm;
  130.     return;
  131. }
  132.  
  133. // Like XtAppAddTimeOut(), but also register timer in internal list.
  134. XtIntervalId MyAppAddTimeOut(XtAppContext app_context,
  135.                  unsigned long interval,
  136.                  XtTimerCallbackProc proc,
  137.                  XtPointer closure,
  138.                  String file, int line)
  139. {
  140.     TimerInfo *tm = new TimerInfo;
  141.     tm->timer    = XtAppAddTimeOut(app_context, interval, 
  142.                    MyTimerProc, XtPointer(tm));
  143.     tm->interval = interval;
  144.     tm->proc     = proc;
  145.     tm->closure  = closure;
  146.     tm->file     = (file ? file : "");
  147.     tm->line     = line;
  148.     tm->tic      = ++timer_tics;
  149.  
  150.     tm->next = pending_timers;
  151.     pending_timers = tm;
  152.  
  153. #if LOG_TIMERS
  154.     clog << "TimeOut: " 
  155.      << file << ":" << line << ": timer " 
  156.      << tm->tic << " (" << XtPointer(tm->timer) << ") added "
  157.      << "(" << MyPendingTimeOuts() << " still pending)\n";
  158. #endif
  159.  
  160.     // Note: we return a private XtIntervalId instead of the one
  161.     // returned by XtAppAddInput.  This gives every timer a unique id
  162.     // and thus enables us to check for expired timers.
  163.     return tm->tic;
  164. }
  165.  
  166. // Like XtRemoveTimeOut(), but unregister TIMER from internal list. 
  167. // Trigger an error if TIMER is not found (i.e. expired or removed)
  168. void MyRemoveTimeOut(XtIntervalId tic, String file, int line)
  169. {
  170.     TimerInfo *tp = 0;
  171.     for (TimerInfo *ti = pending_timers; ti != 0; tp = ti, ti = ti->next)
  172.     {
  173.     if (tic == ti->tic)
  174.     {
  175. #if LOG_TIMERS
  176.         clog << "TimeOut: " << file << ":" << line << ": timer "
  177.          << ti->tic << " (" << XtPointer(ti->timer) << ") removed "
  178.          << "(" << MyPendingTimeOuts() << " still pending)\n"
  179.          << "TimeOut: " << ti->file << ":" << ti->line
  180.          << ": this is the location where the timer was added.\n";
  181. #endif
  182.  
  183.         XtRemoveTimeOut(ti->timer);
  184.  
  185.         if (tp != 0)
  186.         tp->next = ti->next;
  187.         else
  188.         pending_timers = ti->next;
  189.  
  190.         delete ti;
  191.         return;
  192.     }
  193.     }
  194.  
  195.     // Timer not found - either already called or removed
  196.     cerr << "TimeOut: " << file << ":" << line << ": timer " 
  197.      << tic << " expired\n";
  198.  
  199.     // `It is an error to remove a timer that has already gone off.'
  200.     // (Asente/Swick, X WINDOW SYSTEM TOOLKIT, 6.4 `Timers').
  201.     abort();
  202. }
  203.