scheduler.h

Go to the documentation of this file.
00001 /* -*-  Mode:C++; c-basic-offset:8; tab-width:8; indent-tabs-mode:t -*- */
00002 /*
00003  * Copyright (c) 1994 Regents of the University of California.
00004  * All rights reserved.
00005  *
00006  * Redistribution and use in source and binary forms, with or without
00007  * modification, are permitted provided that the following conditions
00008  * are met:
00009  * 1. Redistributions of source code must retain the above copyright
00010  *    notice, this list of conditions and the following disclaimer.
00011  * 2. Redistributions in binary form must reproduce the above copyright
00012  *    notice, this list of conditions and the following disclaimer in the
00013  *    documentation and/or other materials provided with the distribution.
00014  * 3. All advertising materials mentioning features or use of this software
00015  *    must display the following acknowledgement:
00016  *  This product includes software developed by the Computer Systems
00017  *  Engineering Group at Lawrence Berkeley Laboratory.
00018  * 4. Neither the name of the University nor of the Laboratory may be used
00019  *    to endorse or promote products derived from this software without
00020  *    specific prior written permission.
00021  *
00022  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
00023  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00024  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
00025  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
00026  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
00027  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
00028  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
00029  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
00030  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
00031  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
00032  * SUCH DAMAGE.
00033  *
00034  * @(#) $Header: /nfs/jade/vint/CVSROOT/ns-2/common/scheduler.h,v 1.27 2005/07/27 01:13:42 tomh Exp $ (LBL)
00035  */
00036 
00037 #ifndef ns_scheduler_h
00038 #define ns_scheduler_h
00039 
00040 #include "config.h"
00041 
00042 // Make use of 64 bit integers if available.
00043 #ifdef HAVE_INT64
00044 typedef int64_t scheduler_uid_t;
00045 #define UID_PRINTF_FORMAT STRTOI64_FMTSTR
00046 #define STRTOUID(S) STRTOI64((S), NULL, 0)
00047 #else
00048 typedef int scheduler_uid_t;
00049 #define UID_PRINTF_FORMAT "%d"
00050 #define STRTOUID(S) atoi((S))
00051 #endif
00052 
00053 
00054 class Handler;
00055 
00056 class Event {
00057 public:
00058     Event* next_;       /* event list */
00059     Event* prev_;
00060     Handler* handler_;  /* handler to call when event ready */
00061     double time_;       /* time at which event is ready */
00062     scheduler_uid_t uid_;   /* unique ID */
00063     Event() : time_(0), uid_(0) {}
00064 };
00065 
00066 /*
00067  * The base class for all event handlers.  When an event's scheduled
00068  * time arrives, it is passed to handle which must consume it.
00069  * i.e., if it needs to be freed it, it must be freed by the handler.
00070  */
00071 class Handler {
00072  public:
00073     virtual ~Handler () {}
00074     virtual void handle(Event* event) = 0;
00075 };
00076 
00077 #define SCHED_START 0.0 /* start time (secs) */
00078 
00079 class Scheduler : public TclObject {
00080 public:
00081     static Scheduler& instance() {
00082         return (*instance_);        // general access to scheduler
00083     }
00084     void schedule(Handler*, Event*, double delay);  // sched later event
00085     virtual void run();         // execute the simulator
00086     virtual void cancel(Event*) = 0;    // cancel event
00087     virtual void insert(Event*) = 0;    // schedule event
00088     virtual Event* lookup(scheduler_uid_t uid) = 0; // look for event
00089     virtual Event* deque() = 0;     // next event (removes from q)
00090     virtual const Event* head() = 0;    // next event (not removed from q)
00091     double clock() const {          // simulator virtual time
00092         return (clock_);
00093     }
00094     virtual void sync() {};
00095     virtual double start() {        // start time
00096         return SCHED_START;
00097     }
00098     virtual void reset();
00099 protected:
00100     void dumpq();   // for debug: remove + print remaining events
00101     void dispatch(Event*);  // execute an event
00102     void dispatch(Event*, double);  // exec event, set clock_
00103     Scheduler();
00104     virtual ~Scheduler();
00105     int command(int argc, const char*const* argv);
00106     double clock_;
00107     int halted_;
00108     static Scheduler* instance_;
00109     static scheduler_uid_t uid_;
00110 };
00111 
00112 class ListScheduler : public Scheduler {
00113 public:
00114     ListScheduler() : queue_(0) {}
00115     void cancel(Event*);
00116     void insert(Event*);
00117     Event* deque();
00118     const Event* head() { return queue_; }
00119     Event* lookup(scheduler_uid_t uid);
00120 
00121 protected:
00122     Event* queue_;
00123 };
00124 
00125 #include "heap.h"
00126 
00127 class HeapScheduler : public Scheduler {
00128 public:
00129     HeapScheduler() { hp_ = new Heap; } 
00130     void cancel(Event* e) {
00131         if (e->uid_ <= 0)
00132             return;
00133         e->uid_ = - e->uid_;
00134         hp_->heap_delete((void*) e);
00135     }
00136     void insert(Event* e) {
00137         hp_->heap_insert(e->time_, (void*) e);
00138     }
00139     Event* lookup(scheduler_uid_t uid);
00140     Event* deque();
00141     const Event* head() { return (const Event *)hp_->heap_min(); }
00142 protected:
00143     Heap* hp_;
00144 };
00145 
00146 class CalendarScheduler : public Scheduler {
00147 public:
00148     CalendarScheduler();
00149     ~CalendarScheduler();
00150     void cancel(Event*);
00151     void insert(Event*);
00152     Event* lookup(scheduler_uid_t uid);
00153     Event* deque();
00154     const Event* head();
00155 
00156 protected:
00157     double width_;
00158     double diff0_, diff1_, diff2_; /* wrap-around checks */
00159 
00160     int stat_qsize_;        /* # of distinct priorities in queue*/
00161     int nbuckets_;
00162     int lastbucket_;
00163     int top_threshold_;
00164     int bot_threshold_;
00165 
00166     struct Bucket {
00167         Event *list_;
00168         int    count_;
00169     } *buckets_;
00170         
00171     int qsize_;
00172 
00173     virtual void reinit(int nbuck, double bwidth, double start);
00174     virtual void resize(int newsize, double start);
00175     virtual double newwidth(int newsize);
00176 
00177 private:
00178     virtual void insert2(Event*);
00179     double cal_clock_;  // same as clock in sims, may be different in RT-scheduling.
00180 
00181 };
00182 
00183 class SplayScheduler : public Scheduler 
00184 {
00185 public:
00186     SplayScheduler() : root_(0), qsize_(0) {}
00187     void insert(Event *);
00188     Event *deque();
00189     const Event *head();
00190     void cancel(Event *);
00191     Event *lookup(scheduler_uid_t);
00192 
00193     //void validate() { assert(validate(root_) == qsize_); };
00194     
00195 protected:
00196     /* XXX even if debug is enabled, we want these inlined, so
00197        XXX they are defined as macros in splay-scheduler.cc
00198        Event *&LEFT(Event *e)  { return e->prev_; }
00199        Event *&RIGHT(Event *e) { return e->next_; }
00200     */
00201     Event *uid_lookup(Event *);
00202 
00203     Event           *root_;
00204     scheduler_uid_t     lookup_uid_;
00205     int             qsize_;
00206 private:
00207     int validate(Event *);
00208 };
00209 
00210 
00211 #endif

Generated on Tue Mar 6 16:47:50 2007 for ns2 Network Simulator 2.29 by  doxygen 1.4.6