NS2下AODV协议aodv.cc注释(3)

//如果转发的跳数大于到达目的节点的跳数,则进行路由修复;否则丢弃通过此邻居的
//数据并且删除此邻居
  if (ch->num_forwards() > rt->rt_hops) {
    local_rt_repair(rt, p); // local repair
    // retrieve all the packets in the ifq using this link,
    // queue the packets for which local repair is done,
    return;
  }
  else 
#endif // LOCAL REPAIR 

{
    drop(p, DROP_RTR_MAC_CALLBACK);
    // Do the same thing for other packets in the interface queue using the
    // broken link -Mahesh
while((p = ifqueue->filter(broken_nbr))) {
    drop(p, DROP_RTR_MAC_CALLBACK);
    } 
    nb_delete(broken_nbr);
  }

#endif // LINK LAYER DETECTION
}
/*当发现邻居失效的时候,就会调用此函数*/
void
AODV::handle_link_failure(nsaddr_t id) {
aodv_rt_entry *rt, *rtn;
Packet *rerr = Packet::alloc();
struct hdr_aodv_error *re = HDR_AODV_ERROR(rerr);

re->DestCount = 0;
 //查找通过此邻居节点到达目的的路由,
 for(rt = rtable.head(); rt; rt = rtn) {  // for each rt entry
  rtn = rt->rt_link.le_next;
  //如果跳数不是无限大并且下一跳就是失效的邻居
  if ((rt->rt_hops != INFINITY2) && (rt->rt_nexthop == id) ) {
    assert (rt->rt_flags == RTF_UP);
    assert((rt->rt_seqno%2) == 0);
    rt->rt_seqno++;
    re->unreachable_dst[re->DestCount] = rt->rt_dst;
    re->unreachable_dst_seqno[re->DestCount] = rt->rt_seqno;
#ifdef DEBUG
    fprintf(stderr, "%s(%f): %d\t(%d\t%u\t%d)\n", __FUNCTION__, CURRENT_TIME,
      index, re->unreachable_dst[re->DestCount],
      re->unreachable_dst_seqno[re->DestCount], rt->rt_nexthop);
#endif // DEBUG
    re->DestCount += 1;
    rt_down(rt);//将此路由down掉
  }
  // remove the lost neighbor from all the precursor lists
  rt->pc_delete(id);//删除此路由的前缀列表
 } 
/*如果存在通过此邻居到达目的节点的路由,则发送错误报文*/
 if (re->DestCount > 0) {
#ifdef DEBUG
  fprintf(stderr, "%s(%f): %d\tsending RERR...\n", __FUNCTION__, CURRENT_TIME, index);
#endif // DEBUG
  sendError(rerr, false);
 }
 else {
  Packet::free(rerr);
 }
}

void
AODV::local_rt_repair(aodv_rt_entry *rt, Packet *p) {
#ifdef DEBUG
  fprintf(stderr,"%s: Dst - %d\n", __FUNCTION__, rt->rt_dst);
#endif 
  // Buffer the packet
  rqueue.enque(p);

// mark the route as under repair
  rt->rt_flags = RTF_IN_REPAIR;

sendRequest(rt->rt_dst);

// set up a timer interrupt
  Scheduler::instance().schedule(&lrtimer, p->copy(), rt->rt_req_timeout);
}
/*更新路由条目*/
void
AODV::rt_update(aodv_rt_entry *rt, u_int32_t seqnum, u_int16_t metric,
         nsaddr_t nexthop, double expire_time) {

rt->rt_seqno = seqnum;
    rt->rt_hops = metric;
    rt->rt_flags = RTF_UP;
    rt->rt_nexthop = nexthop;
    rt->rt_expire = expire_time;
}
/*将此路由条目down掉*/
void
AODV::rt_down(aodv_rt_entry *rt) {
  /*
  *  Make sure that you don't "down" a route more than once.
  */

if(rt->rt_flags == RTF_DOWN) {
    return;
  }

// assert (rt->rt_seqno%2); // is the seqno odd?
  rt->rt_last_hop_count = rt->rt_hops;
  rt->rt_hops = INFINITY2;
  rt->rt_flags = RTF_DOWN;
  rt->rt_nexthop = 0;
  rt->rt_expire = 0;

} /* rt_down function */

/*
  Route Handling Functions
*/

void
AODV::rt_resolve(Packet *p) {
struct hdr_cmn *ch = HDR_CMN(p);
struct hdr_ip *ih = HDR_IP(p);
aodv_rt_entry *rt;

/*
  *  Set the transmit failure callback.  That
  *  won't change.
  */
  //这是一个指针,具体请看另一篇博客
 ch->xmit_failure_ = aodv_rt_failed_callback;
 ch->xmit_failure_data_ = (void*) this;
 rt = rtable.rt_lookup(ih->daddr());
 if(rt == 0) {
  rt = rtable.rt_add(ih->daddr());
 }

/*
  * If the route is up, forward the packet
  */
 //如果存在路由,则转发
 if(rt->rt_flags == RTF_UP) {
  assert(rt->rt_hops != INFINITY2);
  forward(rt, p, NO_DELAY);
 }
 /*
  *  if I am the source of the packet, then do a Route Request.
  */
 else if(ih->saddr() == index)
 // {
 //如果是源节点且没有到达目的节点的路由,缓存数分组
 //发送路由请求
  rqueue.enque(p);
  sendRequest(rt->rt_dst);
 }
 /*
  * A local repair is in progress. Buffer the packet.
  */
  //如果此路由处于修复状态,则缓存分组
 else if (rt->rt_flags == RTF_IN_REPAIR) {
  rqueue.enque(p);
 }

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:http://www.heiqu.com/ab5562fd35bafa4ee10b3188dd4834ce.html