⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dsrroutetable.cc

📁 Click is a modular router toolkit. To use it you ll need to know how to compile and install the sof
💻 CC
📖 第 1 页 / 共 4 页
字号:
  dsr_source->dsr_len = sizeof(DSRHop) * hop_count + 2;  dsr_source->dsr_segsleft = hop_count;  for (i=0; i<hop_count; i++) {    dsr_source->addr[i]._ip.s_addr = source_route[i+1].addr();    dsr_source->addr[i]._metric = 0; // to be filled in along the way  }  // set the ip dest annotation to the next hop  p->set_dst_ip_anno(source_route[hop_count].addr());  DEBUG_CHATTER(" * added source route header");  return p;}// removes all DSR headers, leaving an ordinary IP packetPacket *DSRRouteTable::strip_headers(Packet *p_in){  WritablePacket *p = p_in->uniqueify();  click_ip *ip = reinterpret_cast<click_ip *>(p->data());  click_dsr *dsr = (click_dsr *)(p->data() + sizeof(click_ip));  assert(ip->ip_p == IP_PROTO_DSR);  // get the length of the DSR headers from the fixed header  unsigned dsr_len = sizeof(click_dsr) + ntohs(dsr->dsr_len);  // save the IP header  click_ip new_ip;  memcpy(&new_ip, ip, sizeof(click_ip));  new_ip.ip_p = dsr->dsr_next_header;  // remove the headers  p->pull(dsr_len);  memcpy(p->data(), &new_ip, sizeof(click_ip));  ip=reinterpret_cast<click_ip *>(p->data());  ip->ip_len=htons(p->length());  ip->ip_sum=0;  ip->ip_sum=click_in_cksum((unsigned char *)ip,sizeof(click_ip));  p->set_ip_header((click_ip*)p->data(),sizeof(click_ip));  DEBUG_CHATTER(" * stripping headers; removed %d bytes\n");  return p;}// takes a RREQ packet, and returns the route which that request has// so far accumulated.  (we then take this route and add it to the// link cache)DSRRouteDSRRouteTable::extract_request_route(const Packet *p_in){  const click_ip *ip = p_in->ip_header();  // address of the node originating the rreq  unsigned src = ip->ip_src.s_addr;  IPAddress src_addr(src);  const click_dsr_rreq *dsr_rreq = (const click_dsr_rreq *)(p_in->data()+							    sizeof(click_ip)+							    sizeof(click_dsr));  assert(dsr_rreq->dsr_type == DSR_TYPE_RREQ);  int num_addr = dsr_rreq->num_addrs();  //  DEBUG_CHATTER(" * hop count in RREQ so far is %d\n", num_addr);  // route is { ip src, addr[0], addr[1], ..., ip dst }  DSRRoute route;  route.push_back(DSRHop(src_addr));  for (int i=0; i<num_addr; i++) {    route.push_back(dsr_rreq->addr[i]);  }  //  IPAddress dst_addr(dsr_rreq->target.s_addr);  //  route.push_back(dst_addr);  return route;}voidDSRRouteTable::issue_rrep(IPAddress src, IPAddress dst,			  DSRRoute reply_route,			  DSRRoute source_route){  // exclude src and dst in source route for hop count  unsigned char src_hop_count = source_route.size() - 2;  // however the reply route has to include the destination.  the  // source is in the IP dest field  unsigned char reply_hop_count = reply_route.size() - 1;  // creating the payload  int payload = (sizeof(click_ip) + sizeof(click_dsr) +		 sizeof(click_dsr_rrep)  +		 sizeof(DSRHop) * reply_hop_count +		 sizeof(click_dsr_source) +		 sizeof(DSRHop) * src_hop_count);  int i;  // XXX?  unsigned ttl=255;  WritablePacket *p = Packet::make(payload);  if (!p) {    DEBUG_CHATTER(" * issue_rrep: couldn't make packet of %d bytes\n", payload);    return;  }  // getting pointers to the headers  click_ip *ip = reinterpret_cast<click_ip *>(p->data());  click_dsr *dsr = (click_dsr *)(p->data() + sizeof(click_ip));  click_dsr_rrep *dsr_rrep = (click_dsr_rrep *)( p->data() +						 sizeof(click_ip) +						 sizeof(click_dsr));  click_dsr_source *dsr_source = (click_dsr_source *)( p->data() +						       sizeof(click_ip) +						       sizeof(click_dsr) +						       sizeof(click_dsr_rrep) +						       sizeof(DSRHop) * reply_hop_count);  p->set_ip_header(ip, sizeof(click_ip));  /* fill the source route header */  dsr_source->dsr_type = DSR_TYPE_SOURCE_ROUTE;  dsr_source->dsr_len = sizeof(DSRHop) * src_hop_count + 2;  dsr_source->dsr_segsleft = src_hop_count;  if (src_hop_count != 0) {    // fill up the source route header using the source_route    // addresses, omitting first and last addresses    for (i=1; i<source_route.size()-1; i++) {      dsr_source->addr[i-1]._ip = source_route[i]._ip;      dsr_source->addr[i-1]._metric = 0; // to be filled in along the way    }  }  // fill the route reply header  dsr_rrep->dsr_type = DSR_TYPE_RREP;  dsr_rrep->dsr_len = sizeof(DSRHop)*reply_hop_count+1;  dsr_rrep->dsr_flags = 0;  //  dsr_rrep->dsr_id = htons(id);  // fill the route reply addrs  for (i=1; i<reply_route.size(); i++) {    // skip first address, which goes in the dest field of the ip    // header.    dsr_rrep->addr[i-1]._ip = reply_route[i]._ip;    dsr_rrep->addr[i-1]._metric = reply_route[i]._metric;  }  // make the IP Header  ip->ip_v = 4;  ip->ip_hl = sizeof(click_ip) >> 2;  ip->ip_len = htons(p->length());  //  ip->ip_id = htons(id); // XXXXX  ip->ip_p = IP_PROTO_DSR;  ip->ip_src.s_addr = src.addr();  ip->ip_dst.s_addr = dst.addr();  ip->ip_tos = 0;  ip->ip_off = 0;  ip->ip_ttl = ttl;  ip->ip_sum = 0;  ip->ip_sum = click_in_cksum((unsigned char *)ip, sizeof(click_ip));  // fill the dsr header  dsr->dsr_next_header = ip->ip_p;  dsr->dsr_len = htons(payload - sizeof(click_dsr) - sizeof(click_ip));  dsr->dsr_reserved = 0;  // setting the next hop annotation  p->set_dst_ip_anno(source_route[1]._ip);  IPAddress dst_anno_address(p->dst_ip_anno());  DEBUG_CHATTER(" * created RREP packet with next hop %s\n", dst_anno_address.unparse().c_str());  output(1).push(p);}// takes info about a bad link from bad_src -> bad_dst, and the// originator of the packet which failed on this link, and sends a// route error along the provided source_routevoidDSRRouteTable::issue_rerr(IPAddress bad_src, IPAddress bad_dst, IPAddress src,			  DSRRoute source_route){  WritablePacket *p = NULL;  // exclude src and dst in source route for hop count  int src_hop_count = source_route.size()-2;  assert(src_hop_count >= 0);  // creating the payload  int payload = (sizeof(click_ip) +		 sizeof(click_dsr) +		 sizeof(click_dsr_rerr)  +		 sizeof(in_addr));  // if the src_hop_count is 0, then no need for a source route option  // XXX handling of rerrs with no SR option is broken; always insert SR option  //   if (src_hop_count > 0)    payload += (sizeof(click_dsr_source) +		sizeof(DSRHop) * (src_hop_count));  int i;  // XXX?  unsigned ttl=255;  // make the packet  p = Packet::make(payload);  if (!p) {    DEBUG_CHATTER(" * issue_rerr:  couldn't make packet of %d bytes\n", payload);    return;  }  // getting pointers to the headers  click_ip *ip = reinterpret_cast<click_ip *>(p->data());  click_dsr *dsr = (click_dsr *)(p->data() + sizeof(click_ip));  click_dsr_rerr *dsr_rerr = (click_dsr_rerr *)(p->data() +						sizeof(click_ip) +						sizeof(click_dsr));  in_addr *dsr_unreach_addr=(in_addr *)(p->data() +					sizeof(click_ip) +					sizeof(click_dsr) +					sizeof(click_dsr_rerr));  click_dsr_source *dsr_source = (click_dsr_source *)(p->data() +						      sizeof(click_ip) +						      sizeof(click_dsr) +						      sizeof(click_dsr_rerr) +						      sizeof(in_addr));  p->set_ip_header(ip, sizeof(click_ip));  // fill in the route error  dsr_rerr->dsr_type = DSR_TYPE_RERR;  dsr_rerr->dsr_len = 14;  dsr_rerr->dsr_error = DSR_RERR_TYPE_NODE_UNREACHABLE;  dsr_rerr->dsr_flags = 0;  dsr_rerr->dsr_err_src.s_addr = bad_src.addr();  dsr_rerr->dsr_err_dst.s_addr = src.addr();  // add unreachable destination  dsr_unreach_addr->s_addr = bad_dst.addr();  // make the IP header  ip->ip_v = 4;  ip->ip_hl = sizeof(click_ip) >> 2;  ip->ip_len = htons(p->length());  // XXX what does the following comment mean?  // id is set to 1..check what value exactly  ip->ip_id = htons(1);  ip->ip_p = IP_PROTO_DSR;  ip->ip_src.s_addr = bad_src.addr();  ip->ip_dst.s_addr = src.addr();  ip->ip_tos = 0;  ip->ip_off = 0;  ip->ip_ttl = ttl;  ip->ip_sum = 0;  ip->ip_sum = click_in_cksum((unsigned char *)ip, sizeof(click_ip));  // fill the dsr header  dsr->dsr_next_header = ip->ip_p;  dsr->dsr_len = htons(payload - sizeof(click_dsr)-sizeof(click_ip));  dsr->dsr_reserved = 0;  // fill in the source route header  // if (src_hop_count > 0) {    // don't need to do this if the target is one hop away    dsr_source->dsr_type = DSR_TYPE_SOURCE_ROUTE;    dsr_source->dsr_len = sizeof(DSRHop) * src_hop_count + 2;    dsr_source->dsr_segsleft = src_hop_count;    // get a pointer to the addresses and fill them up using    // source_route addresses    for (i=1; i < source_route.size()-1; i++) {      dsr_source->addr[i-1]._ip = source_route[i]._ip;      dsr_source->addr[i-1]._metric = 0;    }  //  }  // setting the next hop annotation  p->set_dst_ip_anno(source_route[1]._ip);  IPAddress dst_anno_address(p->dst_ip_anno());  DEBUG_CHATTER(" * created RERR packet with next hop as %s\n",		dst_anno_address.unparse().c_str() );  output(1).push(p);}// takes an RREP packet, copies out the reply route and returns it// as a Vector<IPAddress>DSRRouteDSRRouteTable::extract_reply_route(const Packet *p){  const click_ip *ip = p->ip_header();  const click_dsr_rrep *dsr_rrep = (const click_dsr_rrep *)(p->data()+							    sizeof(click_ip)+							    sizeof(click_dsr));  IPAddress dest_ip(ip->ip_dst.s_addr);  assert(dsr_rrep->dsr_type == DSR_TYPE_RREP);  int hop_count = dsr_rrep->num_addrs();  // DEBUG_CHATTER(" * extracting route from %d-hop route reply\n", hop_count);  DSRRoute route;  // construct the route from the reply addresses.  //  // if the route reply is the result of "reply from cache", then the  // address in the source field of the IP header may differ from the  // destination of the route listed.  so the last hop of the route is  // explicitly specified in the route.  //  // the first hop, however, comes from the destination field of the  // IP header (the intended recipient of this route reply).  so we  // have to put this (dest_ip) first.  route.push_back(DSRHop(dest_ip));  for (int i=0; i < hop_count; i++) {    route.push_back(dsr_rrep->addr[i]);  }  return route;}// returns the source route from this packet; used for producing route// error messages (extract route, truncate at my address, reverse, and// use that as the source route for the route error)DSRRouteDSRRouteTable::extract_source_route(const Packet *p_in, unsigned int offset){  // obtain the pointers to the source route headers  assert(offset < p_in->length());  const click_ip *ip = p_in->ip_header();  const click_dsr_source *dsr_source = (const click_dsr_source *)(p_in->data()+								  offset);  assert(dsr_source->dsr_type == DSR_TYPE_SOURCE_ROUTE);  int source_hops = dsr_source->num_addrs();  DSRRoute route;  // get the source and the destination from the IP Header  IPAddress src(ip->ip_src.s_addr);  IPAddress dst(ip->ip_dst.s_addr);  route.push_back(DSRHop(src));  // append the intermediate nodes to the route  for (int i=0; i<source_hops; i++) {    route.push_back(dsr_source->addr[i]);  }  route.push_back(DSRHop(dst));  return route;}// p_in is a route reply which we received because we're on its source// route; return the packet after setting the IP dest annotationvoidDSRRouteTable::forward_rrep(Packet * p_in){  WritablePacket *p=p_in->uniqueify();  // get pointer to the rrep header  click_dsr_rrep *dsr_rrep=(click_dsr_rrep *)(p->data()+					      sizeof(click_ip) +					      sizeof(click_dsr));  // again, from the draft  int num_addr = dsr_rrep->num_addrs();  //  DEBUG_CHATTER(" * RREP contains %d addresses\n", num_addr);  // XXX originally it seemed there was code here to check if there  // was an additional, "optional" header between the RREP option and  // the source route.  but I don't see any code to actually insert  // this optional header, so I'm leaving this check out for now;  // perhaps the idea is to include some data with the route requests  // and replies?  unsigned int dsr_source_offset = (sizeof(click_ip) +				    sizeof(click_dsr) +				    sizeof(click_dsr_rrep) +				    num_addr * sizeof(DSRHop));  forward_sr(p, dsr_source_offset, 1);}// forwarding a data packet based on the source route option; set the// destination IP anno and return.voidDSRRouteTable::forward_data(Packet *p_in){  forward_sr(p_in, sizeof(click_ip) + sizeof(click_dsr), 2);}// take a wild guess.voidDSRRouteTable::forward_rerr(Packet * p_in){  /* Get the source route pointer */  unsigned int dsr_source_offset = (sizeof(click_ip) +				    sizeof(click_dsr) +				    sizeof(click_dsr_rerr) +				    sizeof(in_addr));  forward_sr(p_in, dsr_source_offset, 1);}IPAddressDSRRouteTable::next_hop(Packet *p){  const click_ip *ip = (const click_ip*)(p->data() + sizeof(click_ether));  click_dsr *dsr = (click_dsr *)(p->data() + sizeof(click_ip));  const unsigned int dsr_len = dsr->dsr_len;  click_dsr_option *dsr_option = (click_dsr_option *)(p->data() +						      sizeof(click_ip) +						      sizeof(click_dsr));  if (dsr_option->dsr_type == DSR_TYPE_RREQ) {    click_chatter("next_hop called on a RREQ?\n");    IPAddress src_addr(0xffffffff);    return (src_addr);  } else if (dsr_option->dsr_type == DSR_TYPE_RREP) {    const click_dsr_rrep *dsr_rrep = (const click_dsr_rrep*)dsr_option;    //    DEBUG_CHATTER(" * extracting IP from route reply; num_addr is %d\n", num_addr);    if (dsr_rrep->length() == dsr_len) {      // if this RREP option is the only option in the header      IPAddress dst_addr(ip->ip_dst.s_addr);      return (dst_addr);    } else {      dsr_option = (click_dsr_option *)(dsr_rrep->next_option());      if (dsr_option->dsr_type != DSR_TYPE_SOURCE_ROUTE) {	click_chatter(" * DSRArpTable::last_hop: source route option did not follow route reply option\n");	IPAddress zeros;	return zeros;      }    }  } else if (dsr_option->dsr_type == DSR_TYPE_RERR) {    // XXX we might have multiple RERRs.    const click_dsr_rerr *dsr_rerr = (click_dsr_rerr *)dsr_option;    if (dsr_rerr->length() == dsr_len) {      // if this RERR option is the only option in the header      IPAddress dst_addr(ip->ip_dst.s_addr);      return (dst_addr);    } else {      dsr_option = (click_dsr_option *)(dsr_rerr->next_option());      if (dsr_option->dsr_type != DSR_TYPE_SOURCE_ROUTE) {	click_chatter(" * source route option did not follow route error option\n");	IPAddress zeros;	return zeros;      }    }  }  if (dsr_option->dsr_type == DSR_TYPE_SOURCE_ROUTE) {

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -