Re: [ns] Fwd: Implementing Round Robin Scheduler
The question is: Are the lines I have commented to solve the problem important or can't affect simulations in any other way? ns-ib.tcl: # # Also reset every queue # #foreach qn [array names link_] { #set q [$link_($qn) queue] #$q reset #} If so, there is an alternative way to solve the problem? Regards, 2012/3/20 Teerawat@UBC teera...@ece.ubc.ca HI Richard, So, what is the question? Best Wishes, Teerawat Issariyakul http://www.ns2ultimate.com/ http://www.facebook.com/pages/Teerawat-Issariyakul/358240861417 http://twitter.com/T_Bear http://www.t-issariyakul.blogspot.com http://www.ece.ubc.ca/~teerawat On Mar 19, 2012, at 11:43 PM, Ricard Alegre wrote: Dear all, I wanted to implement a Round Robin packet scheduler just following the process in the book Introduction to Network Simulator ns2 from Ekran Hossain: According to the process I have created the following *.cc and *.h files: *//classifier-flow.h* #ifndef ns_gw_flow_classifier_h #define ns_gw_flow_classifier_h #include packet.h #include ip.h #include classifier.h class FlowClassifier : public Classifier { protected: int classify(Packet *p); }; #endif *//classifier-flow.cc* #include gw_flow_classifier.h #include stdlib.h static class FlowClassifierClass : public TclClass { public: FlowClassifierClass() : TclClass(Classifier/Flow) {} TclObject* create(int, const char*const*) { return (new FlowClassifier()); } } class_flow_classifier; int FlowClassifier::classify(Packet *p) { return hdr_ip::access(p)-flowid(); } *//pkt-sched.h* #ifndef ns_gw_pkt_sch_h #define ns_gw_pkt_sch_h #include packet.h #include ip.h #include connector.h #include queue.h #define NS 10 class PktScheduler : public Connector { public: PktScheduler(); virtual void handle(Event*); virtual void recv(Packet*, Handler*); protected: void send(int fid, Handler* h); virtual void resume(); int getFlowID(Packet* p) {return hdr_ip::access(p)-flowid();}; virtual int nextID() = 0; Handler* qh_[NS]; Packet* pkt_[NS]; int blocked_; int active_flow_id_; }; //RR class RRScheduler : public PktScheduler { public: RRScheduler(); private: virtual int nextID(); int current_id_; }; #endif *//pkt-sched.cc* #include gw_pkt_sch.h PktScheduler::PktScheduler() { int i; for (i=0;iNS ;i++) { pkt_[i] = 0; qh_[i]=0; } blocked_ = 0;active_flow_id_ = -1; } void PktScheduler::recv(Packet* p, Handler* h) { int fid = getFlowID(p); pkt_[fid] = p;qh_[fid] = h; if (!blocked_) { send(fid,this); blocked_ = 1; active_flow_id_ = fid; } } void PktScheduler::send(int fid_idx, Handler* h) { Connector::send(pkt_[fid_idx],h); pkt_[fid_idx] = 0; } void PktScheduler::handle(Event*) { resume(); } void PktScheduler::resume() { qh_[active_flow_id_]-handle(0); int index = nextID(); blocked_ = 0; if (index = 0) { send(index,this); blocked_ = 1; active_flow_id_ = index; } } //RR RRScheduler::RRScheduler() { current_id_ = -1; } static class RRSchedulerClass: public TclClass { public: RRSchedulerClass() : TclClass(PktScheduler/RR) {} TclObject* create(int, const char*const*) { return (new RRScheduler()); } } class_rr_scheduler; int RRScheduler::nextID() { int count = 0; current_id_++;current_id_ %= NS; while((pkt_[current_id_] == 0)(count NS)){ current_id_++;current_id_ %= NS; count++; } if (count == NS) return -1; else{ return current_id_; } } *And the following Otcl file:* *#ns-link.tcl* Class LinkSch -superclass Link LinkSch instproc init {src dst bw delay num_queues} { $self next $src $dst $self instvar link_ queue_ head_ toNode_ ttl_ $self instvar drophead_ $self instvar num_queues_ sch_ flow_clsfr_ set ns [Simulator instance] set head_ [new Connector] set drophead_ [new Connector] set link_ [new DelayLink] set ttl_ [new TTLChecker] set flow_clsfr_ [new Classifier/Flow] set sch_ [new PktScheduler/RR] set num_queues_ $num_queues $head_ set link_ $self $drophead_ target [$ns set nullAgent_] $head_ target $flow_clsfr_ for {set i 0} {$i $num_queues_} {incr i} { set queue_($i) [new Queue/DropTail] $queue_($i) target $sch_ $queue_($i) drop-target $drophead_ } $sch_ target $link_ $link_ target $ttl_ $link_ drop-target $drophead_ $link_ set bandwidth_ $bw $link_ set delay_ $delay $ttl_ target [$dst entry] $ttl_ drop-target $drophead_ } LinkSch instproc add-flow { fid } { $self instvar queue_ flow_clsfr_
[ns] Fwd: Implementing Round Robin Scheduler
Dear all, I wanted to implement a Round Robin packet scheduler just following the process in the book Introduction to Network Simulator ns2 from Ekran Hossain: According to the process I have created the following *.cc and *.h files: *//classifier-flow.h* #ifndef ns_gw_flow_classifier_h #define ns_gw_flow_classifier_h #include packet.h #include ip.h #include classifier.h class FlowClassifier : public Classifier { protected: int classify(Packet *p); }; #endif *//classifier-flow.cc* #include gw_flow_classifier.h #include stdlib.h static class FlowClassifierClass : public TclClass { public: FlowClassifierClass() : TclClass(Classifier/Flow) {} TclObject* create(int, const char*const*) { return (new FlowClassifier()); } } class_flow_classifier; int FlowClassifier::classify(Packet *p) { return hdr_ip::access(p)-flowid(); } *//pkt-sched.h* #ifndef ns_gw_pkt_sch_h #define ns_gw_pkt_sch_h #include packet.h #include ip.h #include connector.h #include queue.h #define NS 10 class PktScheduler : public Connector { public: PktScheduler(); virtual void handle(Event*); virtual void recv(Packet*, Handler*); protected: void send(int fid, Handler* h); virtual void resume(); int getFlowID(Packet* p) {return hdr_ip::access(p)-flowid();}; virtual int nextID() = 0; Handler* qh_[NS]; Packet* pkt_[NS]; int blocked_; int active_flow_id_; }; //RR class RRScheduler : public PktScheduler { public: RRScheduler(); private: virtual int nextID(); int current_id_; }; #endif *//pkt-sched.cc* #include gw_pkt_sch.h PktScheduler::PktScheduler() { int i; for (i=0;iNS ;i++) { pkt_[i] = 0; qh_[i]=0; } blocked_ = 0;active_flow_id_ = -1; } void PktScheduler::recv(Packet* p, Handler* h) { int fid = getFlowID(p); pkt_[fid] = p;qh_[fid] = h; if (!blocked_) { send(fid,this); blocked_ = 1; active_flow_id_ = fid; } } void PktScheduler::send(int fid_idx, Handler* h) { Connector::send(pkt_[fid_idx],h); pkt_[fid_idx] = 0; } void PktScheduler::handle(Event*) { resume(); } void PktScheduler::resume() { qh_[active_flow_id_]-handle(0); int index = nextID(); blocked_ = 0; if (index = 0) { send(index,this); blocked_ = 1; active_flow_id_ = index; } } //RR RRScheduler::RRScheduler() { current_id_ = -1; } static class RRSchedulerClass: public TclClass { public: RRSchedulerClass() : TclClass(PktScheduler/RR) {} TclObject* create(int, const char*const*) { return (new RRScheduler()); } } class_rr_scheduler; int RRScheduler::nextID() { int count = 0; current_id_++;current_id_ %= NS; while((pkt_[current_id_] == 0)(count NS)){ current_id_++;current_id_ %= NS; count++; } if (count == NS) return -1; else{ return current_id_; } } *And the following Otcl file:* *#ns-link.tcl* Class LinkSch -superclass Link LinkSch instproc init {src dst bw delay num_queues} { $self next $src $dst $self instvar link_ queue_ head_ toNode_ ttl_ $self instvar drophead_ $self instvar num_queues_ sch_ flow_clsfr_ set ns [Simulator instance] set head_ [new Connector] set drophead_ [new Connector] set link_ [new DelayLink] set ttl_ [new TTLChecker] set flow_clsfr_ [new Classifier/Flow] set sch_ [new PktScheduler/RR] set num_queues_ $num_queues $head_ set link_ $self $drophead_ target [$ns set nullAgent_] $head_ target $flow_clsfr_ for {set i 0} {$i $num_queues_} {incr i} { set queue_($i) [new Queue/DropTail] $queue_($i) target $sch_ $queue_($i) drop-target $drophead_ } $sch_ target $link_ $link_ target $ttl_ $link_ drop-target $drophead_ $link_ set bandwidth_ $bw $link_ set delay_ $delay $ttl_ target [$dst entry] $ttl_ drop-target $drophead_ } LinkSch instproc add-flow { fid } { $self instvar queue_ flow_clsfr_ $flow_clsfr_ install $fid $queue_($fid) } Simulator instproc sch-link { n1 n2 bw delay num_queues} { $self instvar link_ queueMap_ nullAgent_ useasim_ set sid [$n1 id] set did [$n2 id] set link_($sid:$did) [new LinkSch $n1 $n2 $bw $delay $num_queues] set pushback 0 $n1 add-neighbor $n2 $pushback } Simulator instproc add-flow { n1 n2 prio } { $self instvar link_ set sid [$n1 id] set did [$n2 id] $link_($sid:$did) add-flow $prio } *The output of the compilation is correct. However, when I try to simulate this tcl script:* set num_queues [lindex $argv 0] set ns [new Simulator] set f [open book.tr w] $ns trace-all $f set n1 [$ns node] set n2 [$ns node] set n3 [$ns node] $ns duplex-link $n1 $n2 5Mb 2ms DropTail $ns duplex-link $n2 $n3 5Mb 2ms DropTail $ns sch-link $n1 $n3 5Mb 2ms 10 $ns simplex-link $n3 $n1 5Mb 2ms DropTail for {set i 0} {$i $num_queues} {incr i} { $ns add-flow $n1 $n3 $i set tcp($i) [new
Re: [ns] Fwd: Implementing Round Robin Scheduler
HI Richard, So, what is the question? Best Wishes, Teerawat Issariyakul http://www.ns2ultimate.com/ http://www.facebook.com/pages/Teerawat-Issariyakul/358240861417 http://twitter.com/T_Bear http://www.t-issariyakul.blogspot.com http://www.ece.ubc.ca/~teerawat On Mar 19, 2012, at 11:43 PM, Ricard Alegre wrote: Dear all, I wanted to implement a Round Robin packet scheduler just following the process in the book Introduction to Network Simulator ns2 from Ekran Hossain: According to the process I have created the following *.cc and *.h files: *//classifier-flow.h* #ifndef ns_gw_flow_classifier_h #define ns_gw_flow_classifier_h #include packet.h #include ip.h #include classifier.h class FlowClassifier : public Classifier { protected: int classify(Packet *p); }; #endif *//classifier-flow.cc* #include gw_flow_classifier.h #include stdlib.h static class FlowClassifierClass : public TclClass { public: FlowClassifierClass() : TclClass(Classifier/Flow) {} TclObject* create(int, const char*const*) { return (new FlowClassifier()); } } class_flow_classifier; int FlowClassifier::classify(Packet *p) { return hdr_ip::access(p)-flowid(); } *//pkt-sched.h* #ifndef ns_gw_pkt_sch_h #define ns_gw_pkt_sch_h #include packet.h #include ip.h #include connector.h #include queue.h #define NS 10 class PktScheduler : public Connector { public: PktScheduler(); virtual void handle(Event*); virtual void recv(Packet*, Handler*); protected: void send(int fid, Handler* h); virtual void resume(); int getFlowID(Packet* p) {return hdr_ip::access(p)-flowid();}; virtual int nextID() = 0; Handler* qh_[NS]; Packet* pkt_[NS]; int blocked_; int active_flow_id_; }; //RR class RRScheduler : public PktScheduler { public: RRScheduler(); private: virtual int nextID(); int current_id_; }; #endif *//pkt-sched.cc* #include gw_pkt_sch.h PktScheduler::PktScheduler() { int i; for (i=0;iNS ;i++) { pkt_[i] = 0; qh_[i]=0; } blocked_ = 0;active_flow_id_ = -1; } void PktScheduler::recv(Packet* p, Handler* h) { int fid = getFlowID(p); pkt_[fid] = p;qh_[fid] = h; if (!blocked_) { send(fid,this); blocked_ = 1; active_flow_id_ = fid; } } void PktScheduler::send(int fid_idx, Handler* h) { Connector::send(pkt_[fid_idx],h); pkt_[fid_idx] = 0; } void PktScheduler::handle(Event*) { resume(); } void PktScheduler::resume() { qh_[active_flow_id_]-handle(0); int index = nextID(); blocked_ = 0; if (index = 0) { send(index,this); blocked_ = 1; active_flow_id_ = index; } } //RR RRScheduler::RRScheduler() { current_id_ = -1; } static class RRSchedulerClass: public TclClass { public: RRSchedulerClass() : TclClass(PktScheduler/RR) {} TclObject* create(int, const char*const*) { return (new RRScheduler()); } } class_rr_scheduler; int RRScheduler::nextID() { int count = 0; current_id_++;current_id_ %= NS; while((pkt_[current_id_] == 0)(count NS)){ current_id_++;current_id_ %= NS; count++; } if (count == NS) return -1; else{ return current_id_; } } *And the following Otcl file:* *#ns-link.tcl* Class LinkSch -superclass Link LinkSch instproc init {src dst bw delay num_queues} { $self next $src $dst $self instvar link_ queue_ head_ toNode_ ttl_ $self instvar drophead_ $self instvar num_queues_ sch_ flow_clsfr_ set ns [Simulator instance] set head_ [new Connector] set drophead_ [new Connector] set link_ [new DelayLink] set ttl_ [new TTLChecker] set flow_clsfr_ [new Classifier/Flow] set sch_ [new PktScheduler/RR] set num_queues_ $num_queues $head_ set link_ $self $drophead_ target [$ns set nullAgent_] $head_ target $flow_clsfr_ for {set i 0} {$i $num_queues_} {incr i} { set queue_($i) [new Queue/DropTail] $queue_($i) target $sch_ $queue_($i) drop-target $drophead_ } $sch_ target $link_ $link_ target $ttl_ $link_ drop-target $drophead_ $link_ set bandwidth_ $bw $link_ set delay_ $delay $ttl_ target [$dst entry] $ttl_ drop-target $drophead_ } LinkSch instproc add-flow { fid } { $self instvar queue_ flow_clsfr_ $flow_clsfr_ install $fid $queue_($fid) } Simulator instproc sch-link { n1 n2 bw delay num_queues} { $self instvar link_ queueMap_ nullAgent_ useasim_ set sid [$n1 id] set did [$n2 id] set link_($sid:$did) [new LinkSch $n1 $n2 $bw $delay $num_queues] set pushback 0 $n1 add-neighbor $n2 $pushback } Simulator instproc add-flow { n1 n2 prio } { $self instvar link_ set sid [$n1 id] set did [$n2 id] $link_($sid:$did) add-flow $prio } *The output of the compilation is correct.