MFlood协议实现

  本协议的实现是作为对NS2扩展的一个实例,将来如果要扩展其他的协议可以参考MFlood协议的实现过程,MFlood在NS2上的扩展已经成功实现,因此记录下扩展过程,对于有需要的人可以进行参考一下。NS2版本为NS2-2.34

  1. 在ns-2.34目录下创建mflood目录,该目录下包括mflood.h(协议类的定义),mflood(协议的实现),mflood-packet.h(包头结构定义),mflood-seqtable.h(路由类定义),seqtable.cc(路由实现)五个文件。
  2. 修改ns-2.34/common/packet.h文件,在文件的申明部分,有一些静态变量申明:static const packet_t PT......修改如下:

  

  在p_info() {
  
      }进行如此扩展。

  3. 修改ns-2.34/tcl/lib/ns-lib.tcl文件

   
    另外再插入这么一段代码:
  
  set前用tab键而不是空格,注意格式保持一致哦。
  4.修改ns-2.34/tcl/lib/ns-packet.tcl文件
  foreach prot {
  
  }
  5.修改ns-2.34/Makefile文件
  OBJ_CC中增加一行:
  
  注意:行末尾以空格加'\'符号结束。
  6.代码实现
  
mflood.h
 1 //mflood.h
2 #ifndef __mflood_h__
3 #define __mflood_h__
4
5 #include <sys/types.h>
6 #include <cmu-trace.h>
7 #include <priqueue.h>
8 #include "mflood/mflood-seqtable.h"
9 #include <list>
10
11 #define NOW (Scheduler::instance().clock())
12
13 //Should be set by the user using best guess (conservative)
14 #define NETWORK_DIAMETER 30 //30 hops
15
16 //The followings are used for the forword() function. Controls pacing
17 #define FORWARD_DELAY 0.01 //random delay
18 #define NO_DELAY -1.0 //no delay
19
20 //The Routing Agent
21 class MFlood: public Agent {
22 friend class MFlood_RTEntry;
23 public:
24 MFlood(nsaddr_t id);
25 void recv(Packet *p, Handler *);
26 protected:
27 int command(int, const char *const *);
28 inline int initialized() {return 1 && target_;}
29 //Route Table Management
30 void rt_resolve(Packet *p);
31 //Packet TX Routines
32 void forward(MFlood_RTEntry *rt, Packet *p, double delay);
33 nsaddr_t index_; //IP Address of this node
34
35
36 //Routing Table
37 MFlood_RTable rtable_;
38 //A mechanism for logging the contents of the routing
39 Trace *logtarget;
40 NsObject *uptarget_;
41 NsObject *port_dmux_;
42 private:
43 u_int32_t myseq_;
44 };
45 #endif
 
mflood.cc
  1 #include "mflood.h"
2 #include "mflood-packet.h"
3 #include <random.h>
4 #include <cmu-trace.h>
5 //New packet type
6 int hdr_mflood::offset_;
7 static class MFloodHeaderClass:public PacketHeaderClass {
8 public:
9 MFloodHeaderClass():PacketHeaderClass("PacketHeader/MFlood",
10 sizeof(hdr_mflood)){
11 bind_offset(&hdr_mflood::offset_);
12 }
13 } class_mfloodhdr;
14
15 //TCL Hooks
16 static class MFloodclass:public TclClass {
17 public:
18 MFloodclass():TclClass("Agent/MFlood"){}
19 TclObject* create(int argc, const char* const* argv){
20 assert(argc == 5);
21 return (new MFlood((nsaddr_t) atoi(argv[4]))); //PBO agrv[4] is index_
22 }
23 } class_rtProtoMFlood;
24
25 int MFlood::command(int argc, const char* const* argv){
26 Tcl& tcl = Tcl::instance();
27 if(argc == 2){
28 if(strncasecmp(argv[1], "id", 2)== 0){
29 tcl.resultf("%d", index_);
30 return TCL_OK;
31 }else if(strcmp(argv[1], "uptarget")== 0){
32 if(uptarget_ != 0)
33 tcl.result(uptarget_ -> name());
34 return (TCL_OK);
35 }
36 }else if(argc == 3){
37 if(strcmp(argv[1], "index_")== 0){
38 index_ = atoi(argv[2]);
39 return TCL_OK;
40 }else if(strcmp(argv[1], "log-target")== 0 || strcmp(argv[1], "tracetarget")== 0) {
41 logtarget = (Trace*)TclObject::lookup(argv[2]);
42 if(logtarget == 0) return TCL_ERROR;
43 return TCL_OK;
44 }else if(strcmp(argv[1], "uptarget")== 0){
45 if(*argv[2] == '0'){
46 target_ = 0;
47 return (TCL_OK);
48 }
49 uptarget_ = (NsObject*)TclObject::lookup(argv[2]);
50 if(uptarget_ == 0){
51 tcl.resultf("no such object %s", argv[2]);
52 return (TCL_ERROR);
53 }
54 return (TCL_OK);
55 }
56 else if (strcasecmp(argv[1], "port-dmux")== 0)
57 {
58 TclObject *obj;
59 port_dmux_ = (NsObject*)obj;
60 return TCL_OK;
61 }
62 }
63 return Agent::command(argc, argv);
64 }
65
66 MFlood::MFlood(nsaddr_t id):Agent(PT_MFLOOD),port_dmux_(0){
67 index_ = id;
68 logtarget = 0;
69 myseq_ = 0;
70 }
71 //Route Handling Functions
72 void MFlood::rt_resolve(Packet *p){
73 struct hdr_cmn *ch = HDR_CMN(p);
74 struct hdr_ip *ih = HDR_IP(p);
75 struct hdr_mflood *fh = HDR_MFLOOD(p);
76 MFlood_RTEntry* rt;
77 rt = rtable_.rt_lookup(ih->saddr());
78 if(rt == NULL){
79 rt = new MFlood_RTEntry(ih->saddr(), fh->seq_);
80 LIST_INSERT_HEAD(&rtable_.rthead,rt,rt_link);
81
82 //printf("%.8f%d, no rt, so forward.rt_seq:%d, pkt seq:%d\n", NOW, index_.rt -> max_seqno, fh -> seq_);
83 forward(rt,p,FORWARD_DELAY);
84 }else if(rt->isNewSeq(fh->seq_)){
85 forward(rt,p,FORWARD_DELAY);
86 rt->addSeq(fh->seq_);
87 }else {
88 drop(p, "LOWSEQ");
89 }
90 }
91
92 //Packet Reception Routines
93 void MFlood::recv(Packet *p, Handler*){
94 struct hdr_cmn *ch = HDR_CMN(p);
95 struct hdr_ip *ih = HDR_IP(p);
96 struct hdr_mflood *fh = HDR_MFLOOD(p);
97 assert(initialized());
98
99 if((ih->saddr() == index_) && (ch->num_forwards() == 0)){
100 //Must be a packet I'm originating...
101 ch->size() += IP_HDR_LEN;
102 ih->ttl_ = NETWORK_DIAMETER;
103 fh->seq_ = myseq_++;
104 forward((MFlood_RTEntry*)1,p,0);
105 return;
106 }else if(ih->saddr() == index_){
107 //I received a packet that I sent. Probably a routing loop.
108 drop(p,DROP_RTR_ROUTE_LOOP);
109 return;
110 }else {
111 //Packet I'm forwarding...
112 if (--ih->ttl_ == 0){
113 //Check the TTL. If it is zero,then discard.
114 drop(p,DROP_RTR_TTL);
115 return;
116 }
117 }
118 rt_resolve(p);
119 }
120
121 //Packet Transmission Routines
122 void MFlood::forward(MFlood_RTEntry* rt, Packet *p, double delay){
123 struct hdr_cmn *ch = HDR_CMN(p);
124 struct hdr_ip *ih = HDR_IP(p);
125 assert(ih->ttl_ > 0);
126 assert(rt != 0);
127 ch -> next_hop_ = -1; //Broadcast address
128 ch -> addr_type() = NS_AF_INET;
129 ch -> direction() = hdr_cmn::DOWN; //important: change the packet's direction
130 if (delay > 0.0){
131 Scheduler::instance().schedule(target_, p, Random::uniform(delay*2));
132 }else {
133 //Not a broadcast packet, no delay, send immediately
134 Scheduler::instance().schedule(target_, p, 0);
135 }
136 }
mfloos-packet.h
 1 #ifndef __mflood_packet_h__
2 #define __mflood_packet_h__
3
4 #define HDR_MFLOOD(p) ((struct hdr_mflood*)hdr_mflood::access(p))
5
6 /*
7 * General MFlood Header
8 */
9 struct hdr_mflood {
10 u_int32_t seq_;
11 //Header access methods
12 static int offset_; //required by PacketHeaderManager
13 inline static int& offset() {return offset_;}
14 inline static hdr_mflood* access(const Packet* p)
15 {
16 return (hdr_mflood*) p -> access(offset_);
17 }
18 };
19
20 #endif
mflood-seqtable.h
 1 #ifndef __mflood_seqtable_h__
2 #define __mflood_seqtable_h__
3 #include <assert.h>
4 #include <sys/types.h>
5 #include <config.h>
6 #include <lib/bsd-list.h>
7 #include <scheduler.h>
8
9 #define INFINITY 0xff
10 #define RTF_DOWN 0
11 #define RTF_UP 1
12 #define REM_SEQ_COUNT 1000
13 //Route Table Entry
14 class MFlood_RTEntry
15 {
16 friend class MFlood_RTable;
17 friend class MFlood;
18 public:
19 MFlood_RTEntry();
20 MFlood_RTEntry(nsaddr_t src, u_int32_t seq);
21 bool isNewSeq(u_int32_t seq); //old false, new true
22 void addSeq(u_int32_t seq); //add a seqno to seqno array(rt_seqnos)
23 protected:
24 LIST_ENTRY(MFlood_RTEntry) rt_link;
25 nsaddr_t src_;
26 u_int32_t rt_seqnos[REM_SEQ_COUNT]; //seqno array
27 u_int32_t max_seqno; //max seqno;
28 u_int32_t min_seqno; //min seqno;
29 u_int16_t seq_it; //seqno iterator
30 };
31
32 //The Routing Table
33 class MFlood_RTable
34 {
35 friend class MFlood;
36 public:
37 MFlood_RTable() {LIST_INIT(&rthead);}
38 void rt_delete(nsaddr_t id);
39 MFlood_RTEntry* rt_lookup(nsaddr_t id);
40 void rt_print();
41 private:
42 LIST_HEAD(, MFlood_RTEntry) rthead;
43 };
44
45 #endif
mflood-seqtable.cc
 1 #include "mflood-seqtable.h"
2 //The Routing Table
3 MFlood_RTEntry::MFlood_RTEntry()
4 {
5 src_ = 0;
6 for (int i = 0; i < REM_SEQ_COUNT; ++i)
7 {
8 rt_seqnos[i] = 0xffffff;
9 max_seqno = 0;
10 min_seqno = 0;
11 seq_it = 0;
12 }
13 };
14
15 //The Routing Table
16 MFlood_RTEntry::MFlood_RTEntry(nsaddr_t src, u_int32_t seq)
17 {
18 src_ = src;
19 for (int i = 0; i < REM_SEQ_COUNT; ++i)
20 {
21 rt_seqnos[i] = 0xffffff;
22 rt_seqnos[0] = seq;
23 max_seqno = seq;
24 min_seqno = 0;
25 seq_it = 1;
26 }
27 };
28
29 bool MFlood_RTEntry::isNewSeq(u_int32_t seq)
30 {
31 if (seq > max_seqno)
32 return true;
33 //discard old packet
34 if (seq < min_seqno)
35 return false;
36 for (int i = 0; i < REM_SEQ_COUNT; ++i)
37 if (seq == rt_seqnos[i])
38 return false;
39 return true;
40 }
41
42 void MFlood_RTEntry::addSeq(u_int32_t seq)
43 {
44 u_int16_t min_it = 0;
45 if (seq < min_seqno)
46 return;
47 if (seq > max_seqno)
48 max_seqno = seq;
49 rt_seqnos[seq_it++] = seq;
50 seq_it %= REM_SEQ_COUNT;
51 min_seqno = 0xffffff;
52 //the value of min_seqno
53 for (int i = 0; i < REM_SEQ_COUNT; ++i)
54 if (min_seqno > rt_seqnos[i])
55 min_seqno = rt_seqnos[i];
56 }
57
58 //The Routing Table
59 MFlood_RTEntry* MFlood_RTable::rt_lookup(nsaddr_t id)
60 {
61 MFlood_RTEntry *rt = rthead.lh_first;
62 for (; rt; rt = rt -> rt_link.le_next)
63 {
64 if (rt -> src_ == id)
65 break;
66 }
67 return rt;
68 }
69
70 void MFlood_RTable::rt_delete(nsaddr_t id)
71 {
72 MFlood_RTEntry *rt = rt_lookup(id);
73 if (rt)
74 {
75 LIST_REMOVE(rt, rt_link);
76 delete rt;
77 }
78 }
79
80 void MFlood_RTable::rt_print()
81 {
82 MFlood_RTEntry *rt = rthead.lh_first;
83 for (; rt; rt = rt -> rt_link.le_next)
84 {
85 //printf("index: %d, seq: %d\n", rt -> src_, rt -> max_seqno);
86 }
87 return;
88 }
 
  如有疑问,可以进行讨论。






转载于:https://www.cnblogs.com/chenxt/archive/2011/11/08/2241145.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值