原文地址:http://blog.csdn.net/qinleopard/article/details/6572175
---------------------------------------
在AODV协议基础上添加一种新的控制包类型,可以模仿AODV协议本身的RREQ、RREP、HELLO等来实现。这里我要在AODV协议中添加一个ISOLATE的数据包类型。
首先在aodv_packet.h中
- #define AODVTYPE_HELLO 0x01
- #define AODVTYPE_RREQ 0x02
- #define AODVTYPE_RREP 0x04
- #define AODVTYPE_RERR 0x08
- #define AODVTYPE_RREP_ACK 0x10
- #define AODVTYPE_ISOLATE 0x20
加入AODVTYPE_ISOLATE 0x20
接着添加数据包申请内存空间的宏
- /*
- * AODV Routing Protocol Header Macros
- */
- #define HDR_AODV(p) ((struct hdr_aodv*)hdr_aodv::access(p))
- #define HDR_AODV_REQUEST(p) ((struct hdr_aodv_request*)hdr_aodv::access(p))
- #define HDR_AODV_REPLY(p) ((struct hdr_aodv_reply*)hdr_aodv::access(p))
- #define HDR_AODV_ERROR(p) ((struct hdr_aodv_error*)hdr_aodv::access(p))
- #define HDR_AODV_RREP_ACK(p) ((struct hdr_aodv_rrep_ack*)hdr_aodv::access(p))
- #define HDR_AODV_ISOLATE(p) ((struct hdr_aodv_isolate*) hdr_aodv::access(p))
接着要具体定义新的数据包格式了。我这里定义的AODV的格式如下所示:
- struct hdr_aodv_isolate {
- u_int8_t iso_type; //类型编号
- u_int8_t reserved[3]; //保留字,没用到
- u_int8_t mal_count; //Malicious node number u_int32_t iso_bcast_id; // Broadcast ID
- nsaddr_t malicious_node_addr[AODV_MAX_ISOLATE]; //malicious
- double obs[AODV_MAX_ISOLATE];
- nsaddr_t src_addr; //源节点
- inline int size() //计算数据包的大小
- {
- int sz = 0;
- /*
- sz = sizeof(u_int8_t) //type
- + sizeof(nsaddr_t) //malicious_node_addr
- + sizeof(nsaddr_t) //src_addr
- + sizeof(u_int32_t) //iso_bcast_id
- */
- sz = (2*mal_count+3) *sizeof(u_int32_t);
- assert(sz);
- return sz;
- }
- };
然后是在hdr_all_aodv添加hdr_aodv_isolate,如下所示:
- // for size calculation of header-space reservation
- union hdr_all_aodv {
- hdr_aodv ah;
- hdr_aodv_request rreq;
- hdr_aodv_reply rrep;
- hdr_aodv_error rerr;
- hdr_aodv_rrep_ack rrep_ack;
- hdr_aodv_isolate iso_err;
- };
添加完数据包的头部之后,接下来的主要工作则是在aodv.cc中如何进行发送和接收ISOLATE数据包的问题了。
首先在aodv.h中添加两个函数:
void sendIsolate(Packet *p);
void recvIsolate(Packet *p);
然后到aodv.cc文件中具体实现这两个函数即可。
- void AODV::sendIsolate(Packet *p)
- {
- //Packet *p = Packet::alloc();
- struct hdr_cmn *ch = HDR_CMN(p);
- struct hdr_ip *ih = HDR_IP(p);
- struct hdr_aodv_isolate * iso = HDR_AODV_ISOLATE(p);
- iso->iso_type = AODVTYPE_ISOLATE;
- //iso->malicious_node_addr = malicious_addr;
- iso->src_addr = index;
- iso->iso_bcast_id = bid++; //骞挎挱ID
- //iso->reserved[0,1,2] = ....
- ch->ptype() = PT_AODV;
- ch->size() = IP_HDR_LEN + iso->size();
- ch->iface() = -2;
- ch->error() = 0;
- ch->addr_type() = NS_AF_NONE;
- ch->next_hop_ = 0;
- ch->prev_hop_ = index;
- ch->direction() = hdr_cmn::DOWN; //important: change the packet's direction
- ih->saddr() = index; //源地址
- ih->daddr() = IP_BROADCAST; //广播分组
- ih->sport() = RT_PORT; //源端口号
- ih->dport() = RT_PORT; //目的端口号
- Scheduler::instance().schedule(target_, p, 0.0); //printf("end sendIsolate, and iso_type= %x /n", iso->iso_type);
- }
具体问题具体分析。
注意在完成这个步骤后,执行的时候会有错误(警告)出现,在这里还要在trace/cmu-trace.cc中添加相应的文件输出格式,也就是输出到.tr文件中该数据包的输出格式。在cmu-trace.cc/format_aodv中添加就行了。
具体什么时候要发送该数据包也是因需求而定,不过你可以设置成周期性地发送该数据包。设置周期性发送的话,你只需要添加一个时钟计数器,然后在时间到达的时候发送该数据包。
添加周期时钟的过程也比较简单。如下所示
首先在aodv.h中添加一个IsolateTimer友元类:
- //Start malicious node isolate
- class IsolateTimer :public Handler{
- public:
- IsolateTimer(AODV *a):agent(a){}
- void handle(Event*);
- private:
- AODV *agent;
- Event intr;
- };
然后把IsolateTimer设置成aodv的友元类
friend class IsolateTimer;
如:
- friend class aodv_rt_entry;
- friend class BroadcastTimer;
- friend class HelloTimer;
- friend class NeighborTimer;
- friend class RouteCacheTimer;
- friend class LocalRepairTimer;
- friend class IsolateTimer; //你的Timer
接着声明一个Timer:
- /*
- * Timers
- */
- BroadcastTimer btimer;
- HelloTimer htimer;
- NeighborTimer ntimer;
- RouteCacheTimer rtimer;
- LocalRepairTimer lrtimer;
- IsolateTimer itimer; //adding isolate packet sending timer
在AODV::AODV的构造函数中初始化以下itimer
- AODV::AODV(nsaddr_t id) : Agent(PT_AODV),
- btimer(this), htimer(this), ntimer(this),
- rtimer(this), lrtimer(this), itimer(this), etimer(this), rqueue() {.............}
然后再到aodv.cc中实现IsolateTimer
- //Start malicious node isolate timer
- void IsolateTimer::handle(Event *)
- {
- agent->isolate_malicious_node();
- double interval = MinIsolateInterval +
- (MaxIsolateInterval-MinIsolateInterval)*Random::uniform();
- assert(interval >=0);
- Scheduler::instance().schedule(this, &intr, interval);
- }
- void AODV::isolate_malicious_node(void)
- {
- int flags = 0;
- malicious *ma = watchdog->mal_List->list;
- neighbour *nb =watchdog->neigs->neigs->group;
- if(watchdog->mal_List->howmany > 0)
- {
- Packet *p = Packet::alloc();
- struct hdr_aodv_isolate * iso = HDR_AODV_ISOLATE(p);
- iso->mal_count = 0; //
- while(ma != NULL)
- {
- iso->malicious_node_addr[iso->mal_count] = ma->ip;
- iso->obs[iso->mal_count] = nb->reputation->obs;
- iso->mal_count++;
- watchdog->delete_malicious_node(ma);
- flags = 1;
- ma = ma->next;
- }
- if(flags==1)//瀛樺湪鏈骞挎挱鐨刴alicious node
- sendIsolate(p);
- }
- }
接下来你调用一下itimer,我是在这里进行调用的:
- int
- AODV::command(int argc, const char*const* argv) {
- ...................
- ..................
- ....................
- else if (strcmp(argv[1], "install-tap") == 0) {
- printf("鎵цinstall-tap /n");
- itimer.handle((Event*) 0); //这里调用了
- mac_ = (Mac*)TclObject::lookup(argv[2]);
- if (mac_ == 0) return TCL_ERROR;
- mac_->installTap(this);
- watchdog->updateMAC(mac_->addr());
- return TCL_OK;
- }
- }
这样就可以完成了。
ps:写得有点乱...哈哈