00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059 extern "C" {
00060 #include <assert.h>
00061 #include <math.h>
00062 #include <stdio.h>
00063 #include <signal.h>
00064 #include <float.h>
00065 }
00066
00067 #include <object.h>
00068 #include <agent.h>
00069 #include <trace.h>
00070 #include <packet.h>
00071 #include <scheduler.h>
00072 #include <random.h>
00073
00074 #include <mac.h>
00075 #include <ll.h>
00076 #include <cmu-trace.h>
00077
00078 #include "path.h"
00079 #include "srpacket.h"
00080 #include "routecache.h"
00081 #include "requesttable.h"
00082 #include "dsragent.h"
00083
00084
00085
00086
00087
00088
00089
00090 #define NEW_SALVAGE_LOGIC
00091
00092 #ifdef NEW_SALVAGE_LOGIC
00093
00094
00095
00096 static int dsr_salvage_max_attempts = 15;
00097
00098
00099
00100
00101 static int dsr_salvage_max_requests = 1;
00102
00103
00104
00105
00106 static bool dsr_salvage_allow_propagating = 0;
00107
00108 #endif
00109
00110
00111 static const bool dsragent_enable_flowstate = true;
00112 static const bool dsragent_prefer_default_flow = true;
00113 static const bool dsragent_prefer_shorter_over_default = true;
00114 static const bool dsragent_always_reestablish = true;
00115 static const int min_adv_interval = 5;
00116 static const int default_flow_timeout = 60;
00117
00118
00119 static const int verbose = 0;
00120 static const int verbose_srr = 0;
00121 static const int verbose_ssalv = 1;
00122
00123 DSRAgent_List DSRAgent::agthead = { 0 };
00124
00125 Time arp_timeout = 30.0e-3;
00126 Time rt_rq_period = 0.5;
00127 Time rt_rq_max_period = 10.0;
00128 Time send_timeout = SEND_TIMEOUT;
00129
00130 #if 0
00131
00132 Time rt_rep_holdoff_period = 3.0e-3;
00133
00134
00135 #endif //0
00136
00137 Time grat_hold_down_time = 1.0;
00138
00139
00140 Time max_err_hold = 1.0;
00141
00142
00143
00144
00145
00146
00147 bool dsragent_snoop_forwarded_errors = true;
00148
00149 bool dsragent_snoop_source_routes = true;
00150
00151 bool dsragent_reply_only_to_first_rtreq = false;
00152
00153 bool dsragent_propagate_last_error = true;
00154
00155
00156
00157 bool dsragent_send_grat_replies = true;
00158
00159 bool dsragent_salvage_with_cache = true;
00160
00161
00162 bool dsragent_use_tap = true;
00163
00164 bool dsragent_reply_from_cache_on_propagating = true;
00165
00166
00167 bool dsragent_ring_zero_search = true;
00168
00169
00170
00171
00172
00173
00174
00175 bool dsragent_dont_salvage_bad_replies = true;
00176
00177
00178
00179
00180 bool dsragent_require_bi_routes = true;
00181
00182
00183
00184
00185 #if 0
00186 bool lsnode_holdoff_rt_reply = true;
00187
00188
00189 bool lsnode_require_use = true;
00190
00191
00192
00193 #endif
00194
00195
00196
00197
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216
00217
00218
00219
00220 void
00221 SendBufferTimer::expire(Event *)
00222 {
00223 a_->sendBufferCheck();
00224 resched(BUFFER_CHECK + BUFFER_CHECK * Random::uniform(1.0));
00225 }
00226
00227 void
00228 DSRAgent::dropSendBuff(SRPacket &p)
00229
00230 {
00231 trace("Ssb %.5f _%s_ dropped %s -> %s", Scheduler::instance().clock(),
00232 net_id.dump(), p.src.dump(), p.dest.dump());
00233 drop(p.pkt, DROP_RTR_QTIMEOUT);
00234 p.pkt = 0;
00235 p.route.reset();
00236 }
00237
00238 void
00239 DSRAgent::stickPacketInSendBuffer(SRPacket& p)
00240 {
00241 Time min = DBL_MAX;
00242 int min_index = 0;
00243 int c;
00244
00245 if (verbose)
00246 trace("Sdebug %.5f _%s_ stuck into send buff %s -> %s",
00247 Scheduler::instance().clock(),
00248 net_id.dump(), p.src.dump(), p.dest.dump());
00249
00250 for (c = 0 ; c < SEND_BUF_SIZE ; c ++)
00251 if (send_buf[c].p.pkt == NULL)
00252 {
00253 send_buf[c].t = Scheduler::instance().clock();
00254 send_buf[c].p = p;
00255 return;
00256 }
00257 else if (send_buf[c].t < min)
00258 {
00259 min = send_buf[c].t;
00260 min_index = c;
00261 }
00262
00263
00264 dropSendBuff(send_buf[min_index].p);
00265 send_buf[min_index].t = Scheduler::instance().clock();
00266 send_buf[min_index].p = p;
00267 }
00268
00269 void
00270 DSRAgent::sendBufferCheck()
00271
00272
00273 {
00274
00275
00276 int c;
00277
00278 for (c = 0 ; c <SEND_BUF_SIZE ; c++) {
00279 if (send_buf[c].p.pkt == NULL)
00280 continue;
00281 if (Scheduler::instance().clock() - send_buf[c].t > send_timeout) {
00282 dropSendBuff(send_buf[c].p);
00283 send_buf[c].p.pkt = 0;
00284 continue;
00285 }
00286 #ifdef DEBUG
00287 trace("Sdebug %.5f _%s_ checking for route for dst %s",
00288 Scheduler::instance().clock(), net_id.dump(),
00289 send_buf[c].p.dest.dump());
00290 #endif
00291
00292 handlePktWithoutSR(send_buf[c].p, true);
00293 #ifdef DEBUG
00294 if (send_buf[c].p.pkt == NULL)
00295 trace("Sdebug %.5f _%s_ sendbuf pkt to %s liberated by handlePktWOSR",
00296 Scheduler::instance().clock(), net_id.dump(),
00297 send_buf[c].p.dest.dump());
00298 #endif
00299 }
00300 }
00301
00302
00303
00304
00305 static bool
00306 BackOffTest(Entry *e, Time time)
00307
00308
00309 {
00310 Time next = ((Time) (0x1 << (e->rt_reqs_outstanding * 2))) * rt_rq_period;
00311
00312 if (next > rt_rq_max_period)
00313 next = rt_rq_max_period;
00314
00315 if (next + e->last_rt_req > time)
00316 return false;
00317
00318
00319 if (e->rt_reqs_outstanding < 15)
00320 e->rt_reqs_outstanding++;
00321
00322 e->last_rt_req = time;
00323
00324 return true;
00325 }
00326
00327
00328
00329
00330 static class DSRAgentClass : public TclClass {
00331 public:
00332 DSRAgentClass() : TclClass("Agent/DSRAgent") {}
00333 TclObject* create(int, const char*const*) {
00334 return (new DSRAgent);
00335 }
00336 } class_DSRAgent;
00337
00338
00339
00340
00341 DSRAgent::DSRAgent(): Agent(PT_DSR), request_table(128), route_cache(NULL),
00342 send_buf_timer(this), flow_table(), ars_table()
00343 {
00344 int c;
00345 route_request_num = 1;
00346
00347 route_cache = makeRouteCache();
00348
00349 for (c = 0 ; c < RTREP_HOLDOFF_SIZE ; c++)
00350 rtrep_holdoff[c].requested_dest = invalid_addr;
00351 num_heldoff_rt_replies = 0;
00352
00353 target_ = 0;
00354 logtarget = 0;
00355
00356 grat_hold_victim = 0;
00357 for (c = 0; c < RTREP_HOLDOFF_SIZE ; c++) {
00358 grat_hold[c].t = 0;
00359 grat_hold[c].p.reset();
00360 }
00361
00362
00363
00364
00365
00366
00367 ll = 0;
00368 ifq = 0;
00369 mac_ = 0;
00370
00371 LIST_INSERT_HEAD(&agthead, this, link);
00372 #ifdef DSR_FILTER_TAP
00373 bzero(tap_uid_cache, sizeof(tap_uid_cache));
00374 #endif
00375 route_error_held = false;
00376 }
00377
00378 DSRAgent::~DSRAgent()
00379 {
00380 fprintf(stderr,"DFU: Don't do this! I haven't figured out ~DSRAgent\n");
00381 exit(-1);
00382 }
00383
00384 void
00385 DSRAgent::Terminate()
00386 {
00387 int c;
00388 for (c = 0 ; c < SEND_BUF_SIZE ; c++) {
00389 if (send_buf[c].p.pkt) {
00390 drop(send_buf[c].p.pkt, DROP_END_OF_SIMULATION);
00391 send_buf[c].p.pkt = 0;
00392 }
00393 }
00394 }
00395
00396 void
00397 DSRAgent::testinit()
00398 {
00399 struct hdr_sr hsr;
00400
00401 if (net_id == ID(1,::IP))
00402 {
00403 printf("adding route to 1\n");
00404 hsr.init();
00405 hsr.append_addr( 1, NS_AF_INET );
00406 hsr.append_addr( 2, NS_AF_INET );
00407 hsr.append_addr( 3, NS_AF_INET );
00408 hsr.append_addr( 4, NS_AF_INET );
00409
00410 route_cache->addRoute(Path(hsr.addrs(),
00411 hsr.num_addrs()), 0.0, ID(1,::IP));
00412 }
00413
00414 if (net_id == ID(3,::IP))
00415 {
00416 printf("adding route to 3\n");
00417 hsr.init();
00418 hsr.append_addr( 3, NS_AF_INET );
00419 hsr.append_addr( 2, NS_AF_INET );
00420 hsr.append_addr( 1, NS_AF_INET );
00421
00422 route_cache->addRoute(Path(hsr.addrs(),
00423 hsr.num_addrs()), 0.0, ID(3,::IP));
00424 }
00425 }
00426
00427
00428 int
00429 DSRAgent::command(int argc, const char*const* argv)
00430 {
00431 TclObject *obj;
00432
00433 if (argc == 2)
00434 {
00435 if (strcasecmp(argv[1], "testinit") == 0)
00436 {
00437 testinit();
00438 return TCL_OK;
00439 }
00440 if (strcasecmp(argv[1], "reset") == 0)
00441 {
00442 Terminate();
00443 return Agent::command(argc, argv);
00444 }
00445 if (strcasecmp(argv[1], "check-cache") == 0)
00446 {
00447 return route_cache->command(argc, argv);
00448 }
00449 if (strcasecmp(argv[1], "startdsr") == 0)
00450 {
00451 if (ID(1,::IP) == net_id)
00452 {
00453 trace("Sconfig %.5f tap: %s snoop: rts? %s errs? %s",
00454 Scheduler::instance().clock(),
00455 dsragent_use_tap ? "on" : "off",
00456 dsragent_snoop_source_routes ? "on" : "off",
00457 dsragent_snoop_forwarded_errors ? "on" : "off");
00458 trace("Sconfig %.5f salvage: %s !bd replies? %s",
00459 Scheduler::instance().clock(),
00460 dsragent_salvage_with_cache ? "on" : "off",
00461 dsragent_dont_salvage_bad_replies ? "on" : "off");
00462 trace("Sconfig %.5f grat error: %s grat reply: %s",
00463 Scheduler::instance().clock(),
00464 dsragent_propagate_last_error ? "on" : "off",
00465 dsragent_send_grat_replies ? "on" : "off");
00466 trace("Sconfig %.5f $reply for props: %s ring 0 search: %s",
00467 Scheduler::instance().clock(),
00468 dsragent_reply_from_cache_on_propagating ? "on" : "off",
00469 dsragent_ring_zero_search ? "on" : "off");
00470 }
00471
00472 send_buf_timer.sched(BUFFER_CHECK
00473 + BUFFER_CHECK * Random::uniform(1.0));
00474 return route_cache->command(argc,argv);
00475 }
00476 }
00477 else if(argc == 3)
00478 {
00479 if (strcasecmp(argv[1], "addr") == 0)
00480 {
00481 int temp;
00482 temp = Address::instance().str2addr(argv[2]);
00483 net_id = ID(temp, ::IP);
00484 flow_table.setNetAddr(net_id.addr);
00485 route_cache->net_id = net_id;
00486 return TCL_OK;
00487 }
00488 else if(strcasecmp(argv[1], "mac-addr") == 0)
00489 {
00490 MAC_id = ID(atoi(argv[2]), ::MAC);
00491 route_cache->MAC_id = MAC_id;
00492 return TCL_OK;
00493 }
00494 else if(strcasecmp(argv[1], "rt_rq_max_period") == 0)
00495 {
00496 rt_rq_max_period = strtod(argv[2],NULL);
00497 return TCL_OK;
00498 }
00499 else if(strcasecmp(argv[1], "rt_rq_period") == 0)
00500 {
00501 rt_rq_period = strtod(argv[2],NULL);
00502 return TCL_OK;
00503 }
00504 else if(strcasecmp(argv[1], "send_timeout") == 0)
00505 {
00506 send_timeout = strtod(argv[2],NULL);
00507 return TCL_OK;
00508 }
00509
00510
00511 if( (obj = TclObject::lookup(argv[2])) == 0)
00512 {
00513 fprintf(stderr, "DSRAgent: %s lookup of %s failed\n", argv[1],
00514 argv[2]);
00515 return TCL_ERROR;
00516 }
00517
00518 if (strcasecmp(argv[1], "log-target") == 0) {
00519 logtarget = (Trace*) obj;
00520 return route_cache->command(argc, argv);
00521 }
00522 else if (strcasecmp(argv[1], "tracetarget") == 0 )
00523 {
00524 logtarget = (Trace*) obj;
00525 return route_cache->command(argc, argv);
00526 }
00527 else if (strcasecmp(argv[1], "install-tap") == 0)
00528 {
00529 mac_ = (Mac*) obj;
00530 mac_->installTap(this);
00531 return TCL_OK;
00532 }
00533 else if (strcasecmp(argv[1], "node") == 0)
00534 {
00535 node_ = (MobileNode *) obj;
00536 return TCL_OK;
00537 }
00538 else if (strcasecmp (argv[1], "port-dmux") == 0)
00539 {
00540 port_dmux_ = (NsObject *) obj;
00541 return TCL_OK;
00542 }
00543 }
00544 else if (argc == 4)
00545 {
00546 if (strcasecmp(argv[1], "add-ll") == 0)
00547 {
00548 if( (obj = TclObject::lookup(argv[2])) == 0) {
00549 fprintf(stderr, "DSRAgent: %s lookup of %s failed\n", argv[1],
00550 argv[2]);
00551 return TCL_ERROR;
00552 }
00553 ll = (NsObject*) obj;
00554 if( (obj = TclObject::lookup(argv[3])) == 0) {
00555 fprintf(stderr, "DSRAgent: %s lookup of %s failed\n", argv[1],
00556 argv[3]);
00557 return TCL_ERROR;
00558 }
00559 ifq = (CMUPriQueue *) obj;
00560 return TCL_OK;
00561
00562 }
00563
00564
00565 }
00566 return Agent::command(argc, argv);
00567 }
00568
00569 void
00570 DSRAgent::sendOutBCastPkt(Packet *p)
00571 {
00572 hdr_cmn *cmh = hdr_cmn::access(p);
00573 if(cmh->direction() == hdr_cmn::UP)
00574 cmh->direction() = hdr_cmn::DOWN;
00575
00576 Scheduler::instance().schedule(ll, p, 0.0);
00577 }
00578
00579
00580
00581 void
00582 DSRAgent::recv(Packet* packet, Handler*)
00583
00584
00585 {
00586 hdr_sr *srh = hdr_sr::access(packet);
00587 hdr_ip *iph = hdr_ip::access(packet);
00588 hdr_cmn *cmh = hdr_cmn::access(packet);
00589
00590
00591 if (cmh->ptype() == PT_GAF) {
00592 if (iph->daddr() == (int)IP_BROADCAST) {
00593 if(cmh->direction() == hdr_cmn::UP)
00594 cmh->direction() = hdr_cmn::DOWN;
00595 Scheduler::instance().schedule(ll,packet,0);
00596 return;
00597 } else {
00598 target_->recv(packet, (Handler*)0);
00599 return;
00600 }
00601 }
00602
00603 assert(cmh->size() >= 0);
00604
00605 SRPacket p(packet, srh);
00606
00607
00608 p.dest = ID((Address::instance().get_nodeaddr(iph->daddr())),::IP);
00609 p.src = ID((Address::instance().get_nodeaddr(iph->saddr())),::IP);
00610
00611 assert(logtarget != 0);
00612
00613 if (srh->valid() != 1) {
00614 unsigned int dst = cmh->next_hop();
00615 if (dst == IP_BROADCAST) {
00616
00617
00618 if (p.src == net_id)
00619
00620 sendOutBCastPkt(packet);
00621 else
00622
00623 port_dmux_->recv(packet, (Handler*)0);
00624
00625 } else {
00626
00627
00628 srh->init();
00629 cmh->size() += IP_HDR_LEN;
00630 if (verbose)
00631 trace("S %.9f _%s_ originating %s -> %s",
00632 Scheduler::instance().clock(), net_id.dump(), p.src.dump(),
00633 p.dest.dump());
00634 handlePktWithoutSR(p, false);
00635 goto done;
00636 }
00637 }
00638 else if (srh->valid() == 1)
00639 {
00640 if (p.dest == net_id || p.dest == IP_broadcast)
00641 {
00642 handlePacketReceipt(p);
00643 goto done;
00644 }
00645
00646
00647
00648 if (dsragent_snoop_forwarded_errors && srh->route_error())
00649 {
00650 processBrokenRouteError(p);
00651 }
00652
00653 if (srh->route_request())
00654 {
00655 handleRouteRequest(p);
00656 }
00657 else
00658 {
00659 handleForwarding(p);
00660 }
00661 }
00662 else {
00663
00664 fprintf(stderr,"dsragent: Error-received Invalid pkt!\n");
00665 Packet::free(p.pkt);
00666 p.pkt =0;
00667 }
00668
00669 done:
00670 assert(p.pkt == 0);
00671
00672 p.pkt = 0;
00673 return;
00674 }
00675
00676
00677
00678
00679
00680 void
00681 DSRAgent::handlePktWithoutSR(SRPacket& p, bool retry)
00682
00683
00684 {
00685 assert(HDR_SR (p.pkt)->valid());
00686
00687 if (p.dest == net_id)
00688 {
00689 handlePacketReceipt(p);
00690 return;
00691 }
00692
00693
00694
00695
00696 ID dest;
00697 if (diff_subnet(p.dest,net_id)) {
00698 dest = ID(node_->base_stn(),::IP);
00699 p.dest = dest;
00700 }
00701
00702 if (route_cache->findRoute(p.dest, p.route, 1))
00703 {
00704 if (verbose)
00705 trace("S$hit %.5f _%s_ %s -> %s %s",
00706 Scheduler::instance().clock(), net_id.dump(),
00707 p.src.dump(), p.dest.dump(), p.route.dump());
00708 sendOutPacketWithRoute(p, true);
00709 return;
00710 }
00711 else
00712 {
00713 if (verbose)
00714 trace("S$miss %.5f _%s_ %s -> %s",
00715 Scheduler::instance().clock(), net_id.dump(),
00716 net_id.dump(), p.dest.dump());
00717
00718 getRouteForPacket(p, retry);
00719 return;
00720 }
00721 }
00722
00723 void
00724 DSRAgent::handlePacketReceipt(SRPacket& p)
00725
00726 {
00727 hdr_cmn *cmh = hdr_cmn::access(p.pkt);
00728 hdr_sr *srh = hdr_sr::access(p.pkt);
00729
00730 if (srh->route_reply())
00731 {
00732
00733
00734 acceptRouteReply(p);
00735 }
00736
00737 if (srh->route_request())
00738 {
00739 if (dsragent_reply_only_to_first_rtreq && ignoreRouteRequestp(p))
00740 {
00741
00742 Packet::free(p.pkt);
00743 p.pkt = 0;
00744 return;
00745 }
00746 else
00747 {
00748 request_table.insert(p.src, p.src, srh->rtreq_seq());
00749 returnSrcRouteToRequestor(p);
00750 }
00751 }
00752
00753 if (srh->route_error())
00754 {
00755 processBrokenRouteError(p);
00756 }
00757
00758 if (srh->flow_unknown())
00759 processUnknownFlowError(p, false);
00760
00761 if (srh->flow_default_unknown())
00762 processUnknownFlowError(p, true);
00763
00764
00765
00766
00767 assert(p.dest == net_id || p.dest == MAC_id);
00768
00769 #if 0
00770 if (iph->dport() == 255) {
00771 int mask = Address::instance().portmask();
00772 int shift = Address::instance().portshift();
00773 iph->daddr() = ((iph->dport() & mask) << shift) | ((~(mask) << shift) & iph->dst());
00774 }
00775 #endif
00776
00777 cmh->size() -= srh->size();
00778 srh->valid() = 0;
00779 cmh->size() -= IP_HDR_LEN;
00780 target_->recv(p.pkt, (Handler*)0);
00781 p.pkt = 0;
00782
00783 }
00784
00785
00786 void
00787 DSRAgent::handleDefaultForwarding(SRPacket &p) {
00788 hdr_ip *iph = hdr_ip::access(p.pkt);
00789 u_int16_t flowid;
00790 int flowidx;
00791
00792 if (!flow_table.defaultFlow(p.src.addr, p.dest.addr, flowid)) {
00793 sendUnknownFlow(p, true);
00794 assert(p.pkt == 0);
00795 return;
00796 }
00797
00798 if ((flowidx = flow_table.find(p.src.addr, p.dest.addr, flowid)) == -1) {
00799 sendUnknownFlow(p, false, flowid);
00800 assert(p.pkt == 0);
00801 return;
00802 }
00803
00804 if (iph->ttl() != flow_table[flowidx].expectedTTL) {
00805 sendUnknownFlow(p, true);
00806 assert(p.pkt == 0);
00807 return;
00808 }
00809
00810
00811
00812 handleFlowForwarding(p, flowidx);
00813 }
00814
00815 void
00816 DSRAgent::handleFlowForwarding(SRPacket &p, int flowidx) {
00817 hdr_sr *srh = hdr_sr::access(p.pkt);
00818 hdr_ip *iph = hdr_ip::access(p.pkt);
00819 hdr_cmn *cmnh = hdr_cmn::access(p.pkt);
00820 int amt;
00821
00822 assert(flowidx >= 0);
00823 assert(!srh->num_addrs());
00824
00825 cmnh->next_hop() = flow_table[flowidx].nextHop;
00826 cmnh->addr_type() = ::IP;
00827
00828 cmnh->xmit_failure_ = XmitFlowFailureCallback;
00829 cmnh->xmit_failure_data_ = (void *) this;
00830
00831
00832
00833 assert(cmnh->direction() == hdr_cmn::UP);
00834
00835 if (!iph->ttl()--) {
00836 drop(p.pkt, DROP_RTR_TTL);
00837 p.pkt = 0;
00838 return;
00839 }
00840
00841 trace("SFf %.9f _%s_ %d [%s -> %s] %d to %d",
00842 Scheduler::instance().clock(), net_id.dump(), cmnh->uid(),
00843 p.src.dump(), p.dest.dump(), flow_table[flowidx].flowId,
00844 flow_table[flowidx].nextHop);
00845
00846
00847 if (!srh->salvaged() &&
00848 (amt = ars_table.findAndClear(cmnh->uid(), flow_table[flowidx].flowId)) &&
00849 p.route.index() - amt > 0) {
00850 trace("SFARS %.9f _%s_ %d [%s -> %s] %d %d",
00851 Scheduler::instance().clock(), net_id.dump(), cmnh->uid(),
00852 p.src.dump(), p.dest.dump(), flow_table[flowidx].flowId, amt);
00853
00854
00855 p.route = flow_table[flowidx].sourceRoute;
00856 p.route.index() -= amt;
00857 sendRouteShortening(p, p.route.index(),
00858 flow_table[flowidx].sourceRoute.index());
00859 }
00860
00861 if (dsragent_always_reestablish) {
00862
00863
00864
00865
00866 flow_table[flowidx].timeout = Scheduler::instance().clock() +
00867 default_flow_timeout;
00868 }
00869
00870 cmnh->direction() = hdr_cmn::DOWN;
00871 Scheduler::instance().schedule(ll, p.pkt, 0);
00872 p.pkt = 0;
00873 }
00874
00875 void
00876 DSRAgent::handleFlowForwarding(SRPacket &p) {
00877 hdr_sr *srh = hdr_sr::access(p.pkt);
00878 hdr_ip *iph = hdr_ip::access(p.pkt);
00879 int flowidx = flow_table.find(p.src.addr, p.dest.addr, srh->flow_id());
00880
00881 assert(srh->flow_header());
00882
00883 if (srh->num_addrs()) {
00884 assert(srh->flow_timeout());
00885
00886 if (flowidx == -1) {
00887 flow_table.cleanup();
00888 flowidx = flow_table.createEntry(p.src.addr, p.dest.addr, srh->flow_id());
00889
00890 assert(flowidx != -1);
00891
00892 flow_table[flowidx].timeout = Scheduler::instance().clock() +
00893 srh->flow_timeout_time();
00894 flow_table[flowidx].hopCount = srh->hopCount();
00895 flow_table[flowidx].expectedTTL = iph->ttl();
00896 flow_table[flowidx].sourceRoute = p.route;
00897 flow_table[flowidx].nextHop = srh->get_next_addr();
00898 assert(srh->hopCount() == srh->cur_addr());
00899 assert(srh->get_next_type() == ::IP);
00900 assert(flow_table[flowidx].sourceRoute[flow_table[flowidx].hopCount] ==
00901 net_id);
00902
00903 flow_table[flowidx].count = 0;
00904 flow_table[flowidx].allowDefault = false;
00905 }
00906
00907 assert(flowidx != -1);
00908
00909
00910 srh->hopCount()++;
00911 return;
00912 }
00913
00914 if (flowidx == -1) {
00915
00916 sendUnknownFlow(p, false, srh->flow_id());
00917 assert(p.pkt == 0);
00918 return;
00919 }
00920
00921
00922
00923 srh->hopCount()++;
00924
00925
00926 handleFlowForwarding(p, flowidx);
00927 }
00928
00929 void
00930 DSRAgent::handleForwarding(SRPacket &p)
00931
00932
00933 {
00934 hdr_sr *srh = hdr_sr::access(p.pkt);
00935 hdr_ip *iph = hdr_ip::access(p.pkt);
00936 hdr_cmn *ch = hdr_cmn::access(p.pkt);
00937 bool flowOnly = !srh->num_addrs();
00938
00939 if (srh->flow_header())
00940 handleFlowForwarding(p);
00941 else if (!srh->num_addrs())
00942 handleDefaultForwarding(p);
00943
00944 if (flowOnly)
00945 return;
00946
00947 assert(p.pkt);
00948
00949
00950
00951 assert(p.route[p.route.index()] == net_id
00952 || p.route[p.route.index()] == MAC_id);
00953
00954 if (p.route.index() >= p.route.length())
00955 {
00956 fprintf(stderr,"dfu: ran off the end of a source route\n");
00957 trace("SDFU: ran off the end of a source route\n");
00958 drop(p.pkt, DROP_RTR_ROUTE_LOOP);
00959 p.pkt = 0;
00960
00961 return;
00962 }
00963
00964
00965 if (dsragent_snoop_source_routes)
00966 route_cache->noticeRouteUsed(p.route, Scheduler::instance().clock(),
00967 net_id);
00968
00969
00970
00971 ch->size() -= srh->size();
00972
00973
00974 if (!iph->ttl()--) {
00975 drop(p.pkt, DROP_RTR_TTL);
00976 p.pkt = 0;
00977 return;
00978 }
00979
00980
00981 sendOutPacketWithRoute(p, false);
00982 }
00983
00984 void
00985 DSRAgent::handleRouteRequest(SRPacket &p)
00986
00987 {
00988 hdr_sr *srh = hdr_sr::access(p.pkt);
00989 assert (srh->route_request());
00990
00991 #ifdef notdef
00992 {
00993 int src = mac_->hdr_src(HDR_MAC(p.pkt));
00994
00995 if(mac_->is_neighbor(src) == 0) {
00996 Packet::free(p.pkt);
00997 p.pkt = 0;
00998 return;
00999 }
01000 }
01001 #endif
01002
01003 if (ignoreRouteRequestp(p))
01004 {
01005 if (verbose_srr)
01006 trace("SRR %.5f _%s_ dropped %s #%d (ignored)",
01007 Scheduler::instance().clock(), net_id.dump(), p.src.dump(),
01008 srh->rtreq_seq());
01009 Packet::free(p.pkt);
01010 p.pkt = 0;
01011 return;
01012 }
01013
01014
01015 request_table.insert(p.src, p.src, srh->rtreq_seq());
01016
01017
01018
01019
01020
01021
01022
01023
01024
01025 if ((srh->max_propagation() == 0 || dsragent_reply_from_cache_on_propagating)
01026 && replyFromRouteCache(p))
01027 return;
01028
01029 #ifdef NEW_REQUEST_LOGIC
01030
01031
01032
01033 if(ifq->prq_length() > 10) {
01034 trace("SRR %.9f _%s_ discarding %s #%d (ifq length %d)",
01035 Scheduler::instance().clock(),
01036 net_id.dump(),
01037 p.src.dump(),
01038 srh->rtreq_seq(),
01039 ifq->prq_length());
01040 Packet::free(p.pkt);
01041 p.pkt = 0;
01042 return;
01043 }
01044
01045
01046
01047
01048 {
01049 double atime = mac_->air_time_free(10);
01050
01051 if(atime > 0.0 && atime < 0.15) {
01052 trace("SRR %.9f _%s_ discarding %s #%d (free air time %f)",
01053 Scheduler::instance().clock(),
01054 net_id.dump(),
01055 p.src.dump(),
01056 srh->rtreq_seq(),
01057 atime);
01058 Packet::free(p.pkt);
01059 p.pkt = 0;
01060 return;
01061 }
01062 }
01063 #endif
01064
01065
01066 if (p.route.length() > srh->max_propagation())
01067 {
01068 if (verbose_srr)
01069 trace("SRR %.5f _%s_ dropped %s #%d (prop limit exceeded)",
01070 Scheduler::instance().clock(), net_id.dump(), p.src.dump(),
01071 srh->rtreq_seq());
01072 Packet::free(p.pkt);
01073 p.pkt = 0;
01074 return;
01075 }
01076
01077
01078 if (p.route.full())
01079 {
01080 trace("SRR %.5f _%s_ dropped %s #%d (SR full)",
01081 Scheduler::instance().clock(), net_id.dump(), p.src.dump(),
01082 srh->rtreq_seq());
01083
01084
01085
01086 Packet::free(p.pkt);
01087 p.pkt = 0;
01088 return;
01089 }
01090
01091
01092 p.route.appendToPath(net_id);
01093
01094 if (verbose_srr)
01095 trace("SRR %.5f _%s_ rebroadcast %s #%d ->%s %s",
01096 Scheduler::instance().clock(), net_id.dump(), p.src.dump(),
01097 srh->rtreq_seq(), p.dest.dump(), p.route.dump());
01098
01099 sendOutPacketWithRoute(p, false);
01100 return;
01101 }
01102
01103
01104
01105
01106 bool
01107 DSRAgent::ignoreRouteRequestp(SRPacket &p)
01108
01109 {
01110 hdr_sr *srh = hdr_sr::access(p.pkt);
01111
01112 if (request_table.get(p.src) >= srh->rtreq_seq())
01113 {
01114
01115 return true;
01116 }
01117 if (p.route.member(net_id,MAC_id))
01118 {
01119 return true;
01120 }
01121
01122 if (p.route.full())
01123 {
01124
01125
01126
01127
01128 return true;
01129 }
01130 return false;
01131 }
01132
01133
01134 bool
01135 DSRAgent::replyFromRouteCache(SRPacket &p)
01136
01137
01138
01139 {
01140 Path rest_of_route;
01141 Path complete_route = p.route;
01142
01143
01144 assert(!p.route.member(net_id, MAC_id));
01145
01146
01147
01148
01149 if (!route_cache->findRoute(p.dest, rest_of_route, 0))
01150 {
01151 return false;
01152 }
01153
01154
01155
01156 assert(rest_of_route[0] == net_id || rest_of_route[0] == MAC_id);
01157
01158 if (rest_of_route.length() + p.route.length() > MAX_SR_LEN)
01159 return false;
01160
01161
01162 complete_route.appendPath(rest_of_route);
01163
01164
01165 ::compressPath(complete_route);
01166
01167 if (!complete_route.member(net_id, MAC_id))
01168 {
01169 return false;
01170 }
01171
01172
01173
01174 hdr_cmn *cmh = hdr_cmn::access(p.pkt);
01175 hdr_sr *srh = hdr_sr::access(p.pkt);
01176 int request_seqnum = srh->rtreq_seq();
01177
01178 if (PT_DSR != cmh->ptype()
01179 || srh->route_reply()
01180 || (srh->route_error() &&
01181 srh->down_links()[srh->num_route_errors()-1].tell_addr
01182 != GRAT_ROUTE_ERROR))
01183 {
01184 SRPacket p_copy = p;
01185 p.pkt = 0;
01186 srh->route_request() = 0;
01187
01188 p_copy.route = complete_route;
01189 p_copy.route.setIterator(p.route.length());
01190
01191 assert(p.route[p.route.index()] == net_id);
01192
01193 if (verbose) trace("Sdebug %.9f _%s_ splitting %s to %s",
01194 Scheduler::instance().clock(), net_id.dump(),
01195 p.route.dump(), p_copy.route.dump());
01196
01197 sendOutPacketWithRoute(p_copy,false);
01198 }
01199 else
01200 {
01201 Packet::free(p.pkt);
01202 p.pkt = 0;
01203 }
01204
01205
01206 p.route.appendToPath(net_id);
01207 p.route.reverseInPlace();
01208 route_cache->addRoute(p.route, Scheduler::instance().clock(), net_id);
01209 p.dest = p.src;
01210 p.src = net_id;
01211 p.pkt = allocpkt();
01212
01213 hdr_ip *iph = hdr_ip::access(p.pkt);
01214 iph->saddr() = Address::instance().create_ipaddr(p.src.addr, RT_PORT);
01215 iph->sport() = RT_PORT;
01216 iph->daddr() = Address::instance().create_ipaddr(p.dest.addr, RT_PORT);
01217 iph->dport() = RT_PORT;
01218 iph->ttl() = 255;
01219
01220 srh = hdr_sr::access(p.pkt);
01221 srh->init();
01222 for (int i = 0 ; i < complete_route.length() ; i++)
01223 complete_route[i].fillSRAddr(srh->reply_addrs()[i]);
01224 srh->route_reply_len() = complete_route.length();
01225 srh->route_reply() = 1;
01226
01227
01228 srh->rtreq_seq() = request_seqnum;
01229
01230 hdr_cmn *cmnh = hdr_cmn::access(p.pkt);
01231 cmnh->ptype() = PT_DSR;
01232 cmnh->size() = IP_HDR_LEN;
01233
01234 if (verbose_srr)
01235 trace("SRR %.9f _%s_ cache-reply-sent %s -> %s #%d (len %d) %s",
01236 Scheduler::instance().clock(), net_id.dump(),
01237 p.src.dump(), p.dest.dump(), request_seqnum, complete_route.length(),
01238 complete_route.dump());
01239 sendOutPacketWithRoute(p, true);
01240 return true;
01241 }
01242
01243
01244 void
01245 DSRAgent::sendOutPacketWithRoute(SRPacket& p, bool fresh, Time delay)
01246
01247
01248
01249
01250
01251 {
01252 hdr_sr *srh = hdr_sr::access(p.pkt);
01253 hdr_cmn *cmnh = hdr_cmn::access(p.pkt);
01254
01255 assert(srh->valid());
01256 assert(cmnh->size() > 0);
01257
01258 ID dest;
01259 if (diff_subnet(p.dest,net_id)) {
01260 dest = ID(node_->base_stn(),::IP);
01261 p.dest = dest;
01262 }
01263
01264 if (p.dest == net_id)
01265 {
01266 recv(p.pkt, (Handler *) 0);
01267 p.pkt = 0;
01268 return;
01269 }
01270
01271 if (fresh)
01272 {
01273 p.route.resetIterator();
01274 if (verbose && !srh->route_request())
01275 {
01276 trace("SO %.9f _%s_ originating %s %s",
01277 Scheduler::instance().clock(),
01278 net_id.dump(), packet_info.name(cmnh->ptype()), p.route.dump());
01279 }
01280 }
01281
01282 p.route.fillSR(srh);
01283
01284
01285 cmnh->direction() = hdr_cmn::DOWN;
01286
01287
01288 if (dsragent_enable_flowstate &&
01289 p.src == net_id && !srh->route_request() && !srh->cur_addr() &&
01290
01291
01292 !srh->route_error() && !srh->route_reply()) {
01293 hdr_ip *iph = hdr_ip::access(p.pkt);
01294 int flowidx;
01295 u_int16_t flowid, default_flowid;
01296 double now = Scheduler::instance().clock();
01297
01298
01299 if (dsragent_prefer_default_flow &&
01300 flow_table.defaultFlow(p.src.addr, p.dest.addr, flowid) &&
01301 -1 != (flowidx = flow_table.find(p.src.addr, p.dest.addr, flowid)) &&
01302 flow_table[flowidx].timeout >= now &&
01303 (!dsragent_prefer_shorter_over_default ||
01304 flow_table[flowidx].sourceRoute.length() <= p.route.length()) &&
01305 !(p.route == flow_table[flowidx].sourceRoute)) {
01306
01307 p.route = flow_table[flowidx].sourceRoute;
01308 p.route.fillSR(srh);
01309 }
01310
01311 flowidx = flow_table.find(p.src.addr, p.dest.addr, p.route);
01312
01313 if (flowidx == -1 || flow_table[flowidx].timeout < now) {
01314
01315 flow_table.cleanup();
01316 flowid = flow_table.generateNextFlowId(p.dest.addr, true);
01317 flowidx = flow_table.createEntry(p.src.addr, p.dest.addr, flowid);
01318 assert(flowidx != -1);
01319
01320
01321 flow_table[flowidx].count = 1;
01322 flow_table[flowidx].lastAdvRt = Scheduler::instance().clock();
01323 flow_table[flowidx].timeout = now + default_flow_timeout;
01324 flow_table[flowidx].hopCount = 0;
01325 flow_table[flowidx].expectedTTL = iph->ttl();
01326 flow_table[flowidx].allowDefault = true;
01327 flow_table[flowidx].sourceRoute = p.route;
01328 flow_table[flowidx].nextHop = srh->get_next_addr();
01329 assert(srh->get_next_type() == ::IP);
01330
01331
01332 srh->flow_timeout() = 1;
01333 srh->flow_timeout_time() = default_flow_timeout;
01334 srh->cur_addr() = srh->cur_addr() + 1;
01335 } else if (flow_table[flowidx].count <= END_TO_END_COUNT ||
01336 flow_table[flowidx].lastAdvRt <
01337 (Scheduler::instance().clock() - min_adv_interval)) {
01338
01339 if (flow_table[flowidx].expectedTTL != iph->ttl())
01340 flow_table[flowidx].allowDefault = false;
01341
01342 flow_table[flowidx].count++;
01343 flow_table[flowidx].lastAdvRt = Scheduler::instance().clock();
01344
01345 srh->flow_timeout() = 1;
01346 if (dsragent_always_reestablish)
01347 srh->flow_timeout_time() = default_flow_timeout;
01348 else
01349 srh->flow_timeout_time() = (int)(flow_table[flowidx].timeout - now);
01350 srh->cur_addr() = srh->cur_addr() + 1;
01351 } else {
01352
01353 assert (flow_table[flowidx].sourceRoute == p.route);
01354 srh->flow_timeout() = srh->cur_addr() = srh->num_addrs() = 0;
01355 }
01356
01357 if (dsragent_always_reestablish) {
01358
01359 flow_table[flowidx].timeout = now + default_flow_timeout;
01360 }
01361
01362 cmnh->next_hop() = flow_table[flowidx].nextHop;
01363 cmnh->addr_type() = ::IP;
01364
01365 if (flow_table.defaultFlow(p.src.addr, p.dest.addr, default_flowid) &&
01366 flow_table[flowidx].flowId == default_flowid &&
01367 !srh->num_addrs() && iph->ttl() == flow_table[flowidx].expectedTTL &&
01368 flow_table[flowidx].allowDefault) {
01369
01370 assert(!srh->flow_header());
01371 } else {
01372 srh->flow_header() = 1;
01373 srh->flow_id() = flow_table[flowidx].flowId;
01374 srh->hopCount() = 1;
01375 }
01376
01377 trace("SF%ss %.9f _%s_ %d [%s -> %s] %d(%d) to %d %s",
01378 srh->num_addrs() ? "EST" : "",
01379 Scheduler::instance().clock(), net_id.dump(), cmnh->uid(),
01380 p.src.dump(), p.dest.dump(), flow_table[flowidx].flowId,
01381 srh->flow_header(), flow_table[flowidx].nextHop,
01382 srh->num_addrs() ? srh->dump() : "");
01383
01384 cmnh->size() += srh->size();
01385 cmnh->xmit_failure_ = srh->num_addrs() ? XmitFailureCallback :
01386 XmitFlowFailureCallback;
01387 cmnh->xmit_failure_data_ = (void *) this;
01388
01389 assert(!srh->num_addrs() || srh->flow_timeout());
01390 } else {
01391
01392 assert(p.src != net_id || !srh->flow_header());
01393 cmnh->size() += srh->size();
01394
01395 if (srh->route_request())
01396 {
01397 cmnh->xmit_failure_ = 0;
01398 cmnh->next_hop() = MAC_BROADCAST;
01399 cmnh->addr_type() = NS_AF_ILINK;
01400 }
01401 else
01402 {
01403 cmnh->xmit_failure_ = XmitFailureCallback;
01404 cmnh->xmit_failure_data_ = (void *) this;
01405
01406 cmnh->next_hop() = srh->get_next_addr();
01407 cmnh->addr_type() = srh->get_next_type();
01408 srh->cur_addr() = srh->cur_addr() + 1;
01409 }
01410 }
01411
01412
01413
01414
01415
01416 #ifdef notdef
01417 if (ifq->prq_length() > 25)
01418 trace("SIFQ %.5f _%s_ len %d",
01419 Scheduler::instance().clock(),
01420 net_id.dump(), ifq->prq_length());
01421 #endif
01422 #ifdef NEW_IFQ_LOGIC
01423
01424
01425
01426
01427
01428
01429
01430
01431 if(ifq->prq_isfull(p.pkt)) {
01432 xmitFailed(p.pkt, DROP_IFQ_QFULL);
01433 p.pkt = 0;
01434 return;
01435 }
01436 #endif
01437
01438
01439 assert(!srh->flow_header() || !srh->num_addrs() || srh->flow_timeout());
01440
01441
01442 if (srh->route_request())
01443 {
01444 Scheduler::instance().schedule(ll, p.pkt,
01445 Random::uniform(RREQ_JITTER) + delay);
01446 }
01447 else
01448 {
01449 Scheduler::instance().schedule(ll, p.pkt, delay);
01450 }
01451 p.pkt = NULL;
01452 }
01453
01454 void
01455 DSRAgent::getRouteForPacket(SRPacket &p, bool retry)
01456
01457
01458
01459 {
01460
01461
01462
01463 Entry *e = request_table.getEntry(p.dest);
01464 Time time = Scheduler::instance().clock();
01465
01466 #if 0
01467
01468
01469
01470
01471
01472
01473
01474 SRPacket rrp = p;
01475 rrp.pkt = p.pkt->copy();
01476 hdr_sr *srh = hdr_sr::access(rrp.pkt);
01477 hdr_ip *iph = hdr_ip::access(rrp.pkt);
01478 hdr_cmn *cmh = hdr_cmn::access(rrp.pkt);
01479
01480 iph->daddr() = Address::instance().create_ipaddr(p.dest.getNSAddr_t(),RT_PORT);
01481 iph->dport() = RT_PORT;
01482
01483 iph->saddr() = Address::instance().create_ipaddr(net_id.getNSAddr_t(),RT_PORT);
01484 iph->sport() = RT_PORT;
01485 cmnh->ptype() = PT_DSR;
01486 cmnh->size() = size_;
01487 cmnh->num_forwards() = 0;
01488 #endif
01489
01490
01491 SRPacket rrp;
01492 rrp.dest = p.dest;
01493 rrp.src = net_id;
01494 rrp.pkt = allocpkt();
01495
01496 hdr_sr *srh = hdr_sr::access(rrp.pkt);
01497 hdr_ip *iph = hdr_ip::access(rrp.pkt);
01498 hdr_cmn *cmnh = hdr_cmn::access(rrp.pkt);
01499
01500 iph->daddr() = Address::instance().create_ipaddr(p.dest.getNSAddr_t(),RT_PORT);
01501 iph->dport() = RT_PORT;
01502 iph->saddr() = Address::instance().create_ipaddr(net_id.getNSAddr_t(),RT_PORT);
01503 iph->sport() = RT_PORT;
01504 cmnh->ptype() = PT_DSR;
01505 cmnh->size() = size_ + IP_HDR_LEN;
01506 cmnh->num_forwards() = 0;
01507
01508 srh->init();
01509
01510
01511 if (BackOffTest(e, time)) {
01512
01513
01514 #ifdef NEW_SALVAGE_LOGIC
01515 if(p.src != net_id) {
01516
01517 assert(dsr_salvage_max_requests > 0);
01518 assert(p.pkt);
01519
01520 if(e->rt_reqs_outstanding > dsr_salvage_max_requests) {
01521 drop(p.pkt, DROP_RTR_NO_ROUTE);
01522 p.pkt = 0;
01523
01524
01525 Packet::free(rrp.pkt);
01526 rrp.pkt = 0;
01527
01528 return;
01529 }
01530 }
01531 #endif
01532
01533 if (dsragent_ring_zero_search) {
01534
01535 e->last_type = LIMIT0;
01536 sendOutRtReq(rrp, 0);
01537 } else {
01538
01539 e->last_type = UNLIMIT;
01540 sendOutRtReq(rrp, MAX_SR_LEN);
01541 }
01542
01543 e->last_arp = time;
01544 } else if (LIMIT0 == e->last_type &&
01545 #ifdef NEW_SALVAGE_LOGIC
01546 (dsr_salvage_allow_propagating || p.src == net_id) &&
01547 #endif
01548 (time - e->last_arp) > arp_timeout) {
01549
01550
01551
01552 e->last_type = UNLIMIT;
01553 sendOutRtReq(rrp, MAX_SR_LEN);
01554 }
01555 else {
01556
01557 if (!retry && verbose_srr)
01558 trace("SRR %.5f _%s_ RR-not-sent %s -> %s",
01559 Scheduler::instance().clock(),
01560 net_id.dump(), rrp.src.dump(), rrp.dest.dump());
01561 Packet::free(rrp.pkt);
01562 rrp.pkt = 0;
01563 }
01564
01565
01566 if (!retry) {
01567 stickPacketInSendBuffer(p);
01568 p.pkt = 0;
01569 }
01570
01571 }
01572
01573 void
01574 DSRAgent::sendOutRtReq(SRPacket &p, int max_prop)
01575
01576
01577
01578 {
01579 hdr_sr *srh = hdr_sr::access(p.pkt);
01580 assert(srh->valid());
01581
01582 srh->route_request() = 1;
01583 srh->rtreq_seq() = route_request_num++;
01584 srh->max_propagation() = max_prop;
01585 p.route.reset();
01586 p.route.appendToPath(net_id);
01587
01588 if (dsragent_propagate_last_error && route_error_held
01589 && Scheduler::instance().clock() - route_error_data_time < max_err_hold)
01590 {
01591 assert(srh->num_route_errors() < MAX_ROUTE_ERRORS);
01592 srh->route_error() = 1;
01593 link_down *deadlink = &(srh->down_links()[srh->num_route_errors()]);
01594 deadlink->addr_type = NS_AF_INET;
01595 deadlink->from_addr = err_from.getNSAddr_t();
01596 deadlink->to_addr = err_to.getNSAddr_t();
01597 deadlink->tell_addr = GRAT_ROUTE_ERROR;
01598 srh->num_route_errors() += 1;
01599
01600
01601
01602 if(max_prop > 0) route_error_held = false;
01603 }
01604
01605 if (verbose_srr)
01606 trace("SRR %.5f _%s_ new-request %d %s #%d -> %s",
01607 Scheduler::instance().clock(), net_id.dump(),
01608 max_prop, p.src.dump(), srh->rtreq_seq(), p.dest.dump());
01609 sendOutPacketWithRoute(p, false);
01610 }
01611
01612 void
01613 DSRAgent::returnSrcRouteToRequestor(SRPacket &p)
01614
01615
01616
01617 {
01618 hdr_sr *old_srh = hdr_sr::access(p.pkt);
01619
01620 if (p.route.full())
01621 return;
01622
01623 SRPacket p_copy = p;
01624 p_copy.pkt = allocpkt();
01625 p_copy.dest = p.src;
01626 p_copy.src = net_id;
01627
01628 p_copy.route.appendToPath(net_id);
01629
01630 hdr_ip *new_iph = hdr_ip::access(p_copy.pkt);
01631
01632 new_iph->daddr() = Address::instance().create_ipaddr(p_copy.dest.getNSAddr_t(),RT_PORT);
01633 new_iph->dport() = RT_PORT;
01634
01635 new_iph->saddr() =
01636 Address::instance().create_ipaddr(p_copy.src.getNSAddr_t(),RT_PORT);
01637 new_iph->sport() = RT_PORT;
01638 new_iph->ttl() = 255;
01639
01640 hdr_sr *new_srh = hdr_sr::access(p_copy.pkt);
01641 new_srh->init();
01642 for (int i = 0 ; i < p_copy.route.length() ; i++)
01643 p_copy.route[i].fillSRAddr(new_srh->reply_addrs()[i]);
01644 new_srh->route_reply_len() = p_copy.route.length();
01645 new_srh->route_reply() = 1;
01646
01647
01648 new_srh->rtreq_seq() = old_srh->rtreq_seq();
01649
01650 hdr_cmn *new_cmnh = hdr_cmn::access(p_copy.pkt);
01651 new_cmnh->ptype() = PT_DSR;
01652 new_cmnh->size() = IP_HDR_LEN;
01653
01654 if (verbose_srr)
01655 trace("SRR %.9f _%s_ reply-sent %s -> %s #%d (len %d) %s",
01656 Scheduler::instance().clock(), net_id.dump(),
01657 p_copy.src.dump(), p_copy.dest.dump(), old_srh->rtreq_seq(),
01658 p_copy.route.length(), p_copy.route.dump());
01659
01660
01661
01662 p_copy.route.reverseInPlace();
01663 route_cache->addRoute(p_copy.route, Scheduler::instance().clock(), net_id);
01664
01665 p_copy.route.resetIterator();
01666 p_copy.route.fillSR(new_srh);
01667 new_cmnh->size() += new_srh->size();
01668
01669
01670
01671
01672
01673 {
01674 double d = Random::uniform(RREQ_JITTER);
01675 #if 0
01676 fprintf(stderr, "Random Delay: %f\n", d);
01677 #endif
01678 Scheduler::instance().schedule(this, p_copy.pkt, d);
01679 }
01680 }
01681
01682 int
01683 DSRAgent::diff_subnet(ID dest, ID myid)
01684 {
01685 int dst = dest.addr;
01686 int id = myid.addr;
01687 char* dstnet = Address::instance().get_subnetaddr(dst);
01688 char * subnet = Address::instance().get_subnetaddr(id);
01689 if (subnet != NULL) {
01690 if (dstnet != NULL) {
01691 if (strcmp(dstnet, subnet) != 0) {
01692 delete [] dstnet;
01693 return 1;
01694 }
01695 delete [] dstnet;
01696 }
01697 delete [] subnet;
01698 }
01699 assert(dstnet == NULL);
01700 return 0;
01701 }
01702
01703
01704 void
01705 DSRAgent::acceptRouteReply(SRPacket &p)
01706
01707
01708
01709 {
01710 hdr_sr *srh = hdr_sr::access(p.pkt);
01711 Path reply_route(srh->reply_addrs(), srh->route_reply_len());
01712
01713 if (!srh->route_reply())
01714 {
01715 trace("SDFU non route containing packet given to acceptRouteReply");
01716 fprintf(stderr,
01717 "dfu: non route containing packet given to acceptRouteReply\n");
01718 }
01719
01720 bool good_reply = true;
01721
01722
01723 int i;
01724
01725 for (i = 0; i < reply_route.length()-1 ; i++)
01726 if (God::instance()->hops(reply_route[i].getNSAddr_t(),
01727 reply_route[i+1].getNSAddr_t()) != 1)
01728 {
01729 good_reply = false;
01730 break;
01731 }
01732
01733
01734 if (verbose_srr)
01735 trace("SRR %.9f _%s_ reply-received %d from %s %s #%d -> %s %s",
01736 Scheduler::instance().clock(), net_id.dump(),
01737 good_reply ? 1 : 0,
01738 p.src.dump(), reply_route[0].dump(), srh->rtreq_seq(),
01739 reply_route[reply_route.length()-1].dump(),
01740 reply_route.dump());
01741
01742
01743 route_cache->addRoute(reply_route, Scheduler::instance().clock(), p.src);
01744
01745
01746 Entry *e = request_table.getEntry(reply_route[reply_route.length()-1]);
01747 e->rt_reqs_outstanding = 0;
01748 e->last_rt_req = 0.0;
01749
01750
01751
01752 Time delay = 0.0;
01753 ID dest;
01754 for (int c = 0; c < SEND_BUF_SIZE; c++)
01755 {
01756 if (send_buf[c].p.pkt == NULL) continue;
01757
01758
01759 if (diff_subnet(send_buf[c].p.dest,net_id)) {
01760 dest = ID(node_->base_stn(),::IP);
01761 send_buf[c].p.dest = dest;
01762 }
01763
01764 if (route_cache->findRoute(send_buf[c].p.dest, send_buf[c].p.route, 1))
01765 {
01766 #ifdef DEBUG
01767 struct hdr_cmn *ch = HDR_CMN(send_buf[c].p.pkt);
01768 if(ch->size() < 0) {
01769 drop(send_buf[c].p.pkt, "XXX");
01770 abort();
01771 }
01772 #endif
01773 if (verbose)
01774 trace("Sdebug %.9f _%s_ liberated from sendbuf %s->%s %s",
01775 Scheduler::instance().clock(), net_id.dump(),
01776 send_buf[c].p.src.dump(), send_buf[c].p.dest.dump(),
01777 send_buf[c].p.route.dump());
01778
01779
01780
01781
01782 sendOutPacketWithRoute(send_buf[c].p, true, delay);
01783 delay += arp_timeout;
01784 send_buf[c].p.pkt = NULL;
01785 }
01786 }
01787 }
01788
01789 void
01790 DSRAgent::processUnknownFlowError(SRPacket &p, bool asDefault) {
01791 hdr_sr *srh = hdr_sr::access(p.pkt);
01792 int flowidx = -1;
01793 struct flow_error *fe;
01794 u_int16_t flowid;
01795
01796 if (asDefault) {
01797 assert (srh->flow_default_unknown() && srh->num_default_unknown());
01798 fe = &srh->unknown_defaults()[srh->num_default_unknown()-1];
01799 } else {
01800 assert (srh->flow_unknown() && srh->num_flow_unknown());
01801 fe = &srh->unknown_flows()[srh->num_flow_unknown()-1];
01802 if (!flow_table.defaultFlow(fe->flow_src, fe->flow_dst, flowid))
01803 goto skip_proc;
01804 }
01805
01806
01807 if (fe->flow_src != (int) net_id.addr)
01808 return;
01809
01810 if (-1 != (flowidx = flow_table.find(fe->flow_src, fe->flow_dst,
01811 asDefault ? flowid : fe->flow_id)))
01812 flow_table[flowidx].count = 0;
01813
01814 skip_proc:
01815 trace("SFEr %.9f _%s_ from %d re %d : %d [%d]",
01816 Scheduler::instance().clock(), net_id.dump(), p.src.addr, fe->flow_dst,
01817 asDefault ? -1 : fe->flow_id,
01818 flowidx != -1 ? flow_table[flowidx].count : -1);
01819
01820 if ((asDefault ? srh->num_default_unknown() : srh->num_flow_unknown()) == 1)
01821 return;
01822
01823 SRPacket p_copy = p;
01824 p_copy.pkt = p.pkt->copy();
01825
01826 hdr_sr *new_srh = hdr_sr::access(p_copy.pkt);
01827 hdr_ip *new_iph = hdr_ip::access(p_copy.pkt);
01828
01829
01830 if (asDefault)
01831 new_srh->num_default_unknown()--;
01832 else
01833 new_srh->num_flow_unknown()--;
01834
01835
01836 p_copy.dest = ID(fe[-1].flow_src, ::IP);
01837 p_copy.src = net_id;
01838
01839
01840 new_iph->daddr() = Address::instance().create_ipaddr(p_copy.dest.getNSAddr_t(),RT_PORT);
01841 new_iph->dport() = RT_PORT;
01842
01843 new_iph->saddr() = Address::instance().create_ipaddr(p_copy.src.getNSAddr_t(),RT_PORT);
01844 new_iph->sport() = RT_PORT;
01845 new_iph->ttl() = 255;
01846
01847 new_srh->flow_header() = 0;
01848 new_srh->flow_timeout() = 0;
01849
01850
01851
01852 handlePktWithoutSR(p_copy, false);
01853 }
01854
01855 void
01856 DSRAgent::processBrokenRouteError(SRPacket& p)
01857
01858
01859
01860 {
01861 hdr_sr *srh = hdr_sr::access(p.pkt);
01862
01863 if (!srh->route_error())
01864 return;
01865
01866
01867
01868
01869
01870
01871
01872 assert(srh->num_route_errors() > 0);
01873 for (int c = 0 ; c < srh->num_route_errors() ; c++)
01874 {
01875 assert(srh->down_links()[c].addr_type == NS_AF_INET);
01876 route_cache->noticeDeadLink(ID(srh->down_links()[c].from_addr,::IP),
01877 ID(srh->down_links()[c].to_addr,::IP),
01878 Scheduler::instance().clock());
01879 flow_table.noticeDeadLink(ID(srh->down_links()[c].from_addr,::IP),
01880 ID(srh->down_links()[c].to_addr,::IP));
01881
01882 if (verbose_srr)
01883 trace("SRR %.9f _%s_ dead-link tell %d %d -> %d",
01884 Scheduler::instance().clock(), net_id.dump(),
01885 srh->down_links()[c].tell_addr,
01886 srh->down_links()[c].from_addr,
01887 srh->down_links()[c].to_addr);
01888 }
01889
01890 ID who = ID(srh->down_links()[srh->num_route_errors()-1].tell_addr, ::IP);
01891 if (who != net_id && who != MAC_id)
01892 {
01893
01894 return;
01895 }
01896
01897
01898
01899 route_error_held = true;
01900 err_from = ID(srh->down_links()[srh->num_route_errors()-1].from_addr,::IP);
01901 err_to = ID(srh->down_links()[srh->num_route_errors()-1].to_addr,::IP);
01902 route_error_data_time = Scheduler::instance().clock();
01903
01904 if (1 == srh->num_route_errors())
01905 {
01906
01907
01908
01909 return;
01910 }
01911
01912
01913
01914
01915 if (verbose)
01916 trace("Sdebug %.5f _%s_ unwrapping nested route error",
01917 Scheduler::instance().clock(), net_id.dump());
01918
01919 SRPacket p_copy = p;
01920 p_copy.pkt = p.pkt->copy();
01921
01922 hdr_sr *new_srh = hdr_sr::access(p_copy.pkt);
01923 hdr_ip *new_iph = hdr_ip::access(p_copy.pkt);
01924
01925
01926 new_srh->num_route_errors() -= 1;
01927
01928
01929 p_copy.dest = ID(new_srh->down_links()[new_srh->num_route_errors()-1].tell_addr, ::IP);
01930 p_copy.src = net_id;
01931
01932
01933 new_iph->daddr() = Address::instance().create_ipaddr(p_copy.dest.getNSAddr_t(),RT_PORT);
01934 new_iph->dport() = RT_PORT;
01935
01936 new_iph->saddr() = Address::instance().create_ipaddr(p_copy.src.getNSAddr_t(),RT_PORT);
01937 new_iph->sport() = RT_PORT;
01938 new_iph->ttl() = 255;
01939
01940 new_srh->flow_header() = 0;
01941 new_srh->flow_timeout() = 0;
01942
01943
01944
01945 handlePktWithoutSR(p_copy, false);
01946 }
01947
01948 #ifdef DSR_FILTER_TAP
01949 int64_t dsr_tap = 0;
01950 int64_t dsr_tap_skip = 0;
01951 #endif
01952
01953
01954 void
01955 DSRAgent::processFlowARS(const Packet *packet) {
01956
01957 hdr_sr *srh = hdr_sr::access(packet);
01958 hdr_ip *iph = hdr_ip::access(packet);
01959 hdr_cmn *cmh = hdr_cmn::access(packet);
01960
01961
01962
01963 u_int16_t flowid;
01964 int flowidx;
01965 int shortamt;
01966
01967 assert(!srh->num_addrs());
01968
01969 if (srh->flow_header()) {
01970 flowid = srh->flow_id();
01971
01972
01973 if (-1 == (flowidx = flow_table.find(iph->saddr(), iph->daddr(), flowid)))
01974 return;
01975
01976 shortamt = flow_table[flowidx].hopCount - srh->hopCount();
01977 } else {
01978
01979 if (!flow_table.defaultFlow(iph->saddr(), iph->daddr(), flowid))
01980 return;
01981
01982
01983 if (-1 == (flowidx = flow_table.find(iph->saddr(), iph->daddr(), flowid)))
01984 return;
01985
01986 shortamt = iph->ttl() - flow_table[flowidx].expectedTTL;
01987 }
01988
01989
01990 if (shortamt <= 0)
01991 return;
01992
01993
01994 if (flow_table[flowidx].sourceRoute.length() < shortamt)
01995 return;
01996
01997 ars_table.insert(cmh->uid(), flowid, shortamt);
01998 }
01999
02000 void
02001 DSRAgent::tap(const Packet *packet)
02002
02003
02004 {
02005 hdr_sr *srh = hdr_sr::access(packet);
02006 hdr_ip *iph = hdr_ip::access(packet);
02007 hdr_cmn *cmh = hdr_cmn::access(packet);
02008
02009 if (!dsragent_use_tap) return;
02010
02011 if (!srh->valid()) return;
02012
02013 if (!srh->num_addrs()) {
02014 processFlowARS(packet);
02015 return;
02016 }
02017
02018
02019
02020 ID next_hop(srh->addrs()[srh->cur_addr()]);
02021 if (next_hop == net_id || next_hop == MAC_id) return;
02022
02023 SRPacket p((Packet *) packet, srh);
02024
02025
02026 p.dest = ID((Address::instance().get_nodeaddr(iph->daddr())),::IP);
02027 p.src = ID((Address::instance().get_nodeaddr(iph->saddr())),::IP);
02028
02029
02030 if (p.src == net_id) return;
02031
02032 #ifdef DSR_FILTER_TAP
02033
02034
02035
02036
02037
02038 {
02039 int uid = cmh->uid();
02040 if(tap_uid_cache[(uid & TAP_BITMASK)] == uid) {
02041 dsr_tap_skip++;
02042 return;
02043 }
02044 dsr_tap++;
02045 tap_uid_cache[(uid & TAP_BITMASK)] = uid;
02046 }
02047 #endif
02048
02049
02050 if (srh->route_error())
02051 {
02052 if (verbose)
02053 trace("Sdebug _%s_ tap saw error %d", net_id.dump(), cmh->uid());
02054 processBrokenRouteError(p);
02055 }
02056
02057 if (srh->route_reply())
02058 {
02059 Path reply_path(srh->reply_addrs(), srh->route_reply_len());
02060 if(verbose)
02061 trace("Sdebug _%s_ tap saw route reply %d %s",
02062 net_id.dump(), cmh->uid(), reply_path.dump());
02063 route_cache->noticeRouteUsed(reply_path, Scheduler::instance().clock(),
02064 p.src);
02065 }
02066
02067
02068
02069
02070
02071
02072 if (srh->route_request()) return;
02073
02074
02075 if (dsragent_snoop_source_routes)
02076 {
02077 if (verbose)
02078 trace("Sdebug _%s_ tap saw route use %d %s", net_id.dump(),
02079 cmh->uid(), p.route.dump());
02080 route_cache->noticeRouteUsed(p.route, Scheduler::instance().clock(),
02081 net_id);
02082 }
02083
02084 if (PT_DSR == cmh->ptype()) return;
02085
02086
02087
02088
02089
02090
02091
02092
02093
02094
02095
02096
02097
02098
02099
02100
02101
02102
02103
02104
02105
02106
02107
02108
02109
02110
02111
02112
02113
02114
02115
02116
02117
02118
02119
02120
02121
02122
02123
02124
02125
02126
02127
02128
02129
02130
02131
02132
02133
02134
02135
02136 if (p.route[p.route.index()] != net_id
02137 && p.route[p.route.index()] != MAC_id)
02138 {
02139 for (int i = p.route.index() + 1; i < p.route.length(); i++)
02140 if (p.route[i] == net_id || p.route[i] == MAC_id)
02141 {
02142 sendRouteShortening(p, p.route.index(), i);
02143 }
02144 }
02145 }
02146
02147 static GratReplyHoldDown *
02148 FindGratHoldDown(GratReplyHoldDown *hd, int sz, Path& query)
02149 {
02150 int c;
02151 for (c = 0; c < sz; c++)
02152 if (query == hd[c].p) return &hd[c];
02153 return NULL;
02154 }
02155
02156 void
02157 DSRAgent::sendRouteShortening(SRPacket &p, int heard_at, int xmit_at)
02158
02159
02160
02161
02162 {
02163
02164
02165 if (!dsragent_send_grat_replies) return;
02166
02167 if (verbose)
02168 trace("Sdebug %s consider grat arp for %s", net_id.dump(), p.route.dump());
02169 GratReplyHoldDown *g = FindGratHoldDown(grat_hold, RTREP_HOLDOFF_SIZE,
02170 p.route);
02171 if (!g)
02172 {
02173 grat_hold[grat_hold_victim].p = p.route;
02174 grat_hold_victim = (grat_hold_victim + 1) % RTREP_HOLDOFF_SIZE;
02175 g = &grat_hold[grat_hold_victim];
02176 }
02177 else if (Scheduler::instance().clock() - g->t < grat_hold_down_time) return;
02178 g->t = Scheduler::instance().clock();
02179
02180 SRPacket p_copy = p;
02181 p_copy.pkt = allocpkt();
02182 p_copy.dest = p.route[0];
02183 p_copy.src = net_id;
02184
02185
02186 p_copy.route[p_copy.route.index()] = net_id;
02187 p_copy.route.reverseInPlace();
02188 p_copy.route.removeSection(0,p_copy.route.index());
02189
02190 hdr_ip *new_iph = hdr_ip::access(p_copy.pkt);
02191
02192 new_iph->daddr() = Address::instance().create_ipaddr(p_copy.dest.getNSAddr_t(),RT_PORT);
02193 new_iph->dport() = RT_PORT;
02194
02195 new_iph->saddr() = Address::instance().create_ipaddr(p_copy.src.getNSAddr_t(),RT_PORT);
02196 new_iph->sport() = RT_PORT;
02197 new_iph->ttl() = 255;
02198
02199
02200 p.route.removeSection(heard_at, xmit_at);
02201 hdr_sr *new_srh = hdr_sr::access(p_copy.pkt);
02202 new_srh->init();
02203 for (int i = 0 ; i < p.route.length() ; i++)
02204 p.route[i].fillSRAddr(new_srh->reply_addrs()[i]);
02205 new_srh->route_reply_len() = p.route.length();
02206 new_srh->route_reply() = 1;
02207
02208 new_srh->rtreq_seq() = 0;
02209
02210 hdr_cmn *new_cmnh = hdr_cmn::access(p_copy.pkt);
02211 new_cmnh->ptype() = PT_DSR;
02212 new_cmnh->size() += IP_HDR_LEN;
02213
02214 if (verbose_srr)
02215 trace("SRR %.9f _%s_ gratuitous-reply-sent %s -> %s (len %d) %s",
02216 Scheduler::instance().clock(), net_id.dump(),
02217 p_copy.src.dump(), p_copy.dest.dump(), p.route.length(),
02218 p.route.dump());
02219
02220
02221 route_cache->addRoute(p_copy.route, Scheduler::instance().clock(), p.src);
02222 sendOutPacketWithRoute(p_copy, true);
02223 }
02224
02225
02226
02227
02228 void
02229 DSRAgent::trace(char* fmt, ...)
02230 {
02231 va_list ap;
02232
02233 if (!logtarget) return;
02234
02235 va_start(ap, fmt);
02236 vsprintf(logtarget->pt_->buffer(), fmt, ap);
02237 logtarget->pt_->dump();
02238 va_end(ap);
02239 }
02240
02241
02242
02243
02244
02245
02246
02247
02248
02249
02250
02251
02252
02253
02254
02255
02256
02257
02258
02259
02260
02261
02262
02263
02264
02265
02266
02267
02268 void
02269 DSRAgent::undeliverablePkt(Packet *pkt, int mine)
02270
02271
02272 {
02273 hdr_sr *srh = hdr_sr::access(pkt);
02274 hdr_ip *iph = hdr_ip::access(pkt);
02275 hdr_cmn *cmh;
02276
02277 SRPacket p(pkt,srh);
02278
02279
02280 p.dest = ID((Address::instance().get_nodeaddr(iph->daddr())),::IP);
02281 p.src = ID((Address::instance().get_nodeaddr(iph->saddr())),::IP);
02282 p.pkt = mine ? pkt : pkt->copy();
02283
02284 srh = hdr_sr::access(p.pkt);
02285 iph = hdr_ip::access(p.pkt);
02286 cmh = hdr_cmn::access(p.pkt);
02287
02288
02289
02290 cmh->size() -= srh->size();
02291 srh->flow_timeout() = 0;
02292 srh->flow_header() = 0;
02293 cmh->size() += srh->size();
02294
02295 if (ID((Address::instance().get_nodeaddr(iph->saddr())),::IP) == net_id) {
02296
02297 cmh->size() -= srh->size();
02298 assert(cmh->size() >= 0);
02299
02300 handlePktWithoutSR(p, false);
02301
02302 return;
02303 }
02304
02305
02306
02307
02308 if(dsragent_salvage_with_cache == 0) {
02309 assert(mine);
02310 drop(pkt, DROP_RTR_NO_ROUTE);
02311 return;
02312 }
02313
02314 #ifdef NEW_SALVAGE_LOGIC
02315 if(srh->salvaged() >= dsr_salvage_max_attempts) {
02316 assert(mine);
02317 drop(pkt, DROP_RTR_SALVAGE);
02318 return;
02319 }
02320 #endif
02321
02322
02323 Path salvage_route;
02324
02325 if (route_cache->findRoute(p.dest, salvage_route, 0)) {
02326
02327 #if 0
02328
02329
02330
02331
02332
02333
02334
02335
02336
02337
02338
02339
02340
02341
02342
02343
02344 int our_index = p.route.index();
02345
02346 p.route.setLength(our_index);
02347
02348
02349 p.route.appendPath(salvage_route);
02350
02351 p.route.setIterator(our_index);
02352 #else
02353 p.route = salvage_route;
02354 p.route.resetIterator();
02355 #endif
02356
02357 if (dsragent_dont_salvage_bad_replies && srh->route_reply()) {
02358
02359
02360
02361 ID to_id(srh->addrs()[srh->cur_addr()+1].addr,
02362 (ID_Type) srh->addrs()[srh->cur_addr()].addr_type);
02363 bool bad_reply = false;
02364
02365 for (int i = 0 ; i < srh->route_reply_len()-1; i++) {
02366
02367 if (net_id == ID(srh->reply_addrs()[i]) &&
02368 to_id == ID(srh->reply_addrs()[i+1]) ||
02369 (dsragent_require_bi_routes &&
02370 to_id == ID(srh->reply_addrs()[i]) &&
02371 net_id == ID(srh->reply_addrs()[i+1]))) {
02372
02373 bad_reply = true;
02374 break;
02375 }
02376 }
02377 if (bad_reply) {
02378
02379 srh->route_reply() = 0;
02380 if (PT_DSR == cmh->ptype() &&
02381 ! srh->route_request() &&
02382 ! srh->route_error()) {
02383
02384 if (verbose_srr)
02385 trace("SRR %.5f _%s_ --- %d dropping bad-reply %s -> %s",
02386 Scheduler::instance().clock(), net_id.dump(),
02387 cmh->uid(), p.src.dump(), p.dest.dump());
02388 if (mine)
02389 drop(pkt, DROP_RTR_MAC_CALLBACK);
02390 return;
02391 }
02392 }
02393 }
02394
02395 if (verbose_ssalv)
02396 trace("Ssalv %.5f _%s_ salvaging %s -> %s --- %d with %s",
02397 Scheduler::instance().clock(), net_id.dump(),
02398 p.src.dump(), p.dest.dump(),
02399 cmh->uid(), p.route.dump());
02400
02401
02402 cmh->size() -= srh->size();
02403 assert(cmh->size() >= 0);
02404 #ifdef NEW_SALVAGE_LOGIC
02405 srh->salvaged() += 1;
02406 #endif
02407 sendOutPacketWithRoute(p, false);
02408 }
02409 #ifdef NEW_SALVAGE_LOGIC
02410 else if(dsr_salvage_max_requests > 0) {
02411
02412
02413
02414
02415 if (verbose_ssalv)
02416 trace("Ssalv %.5f _%s_ adding to SB --- %d %s -> %s [%d]",
02417 Scheduler::instance().clock(),
02418 net_id.dump(),
02419 cmh->uid(),
02420 p.src.dump(), p.dest.dump(),
02421 srh->salvaged());
02422 stickPacketInSendBuffer(p);
02423 }
02424 #endif
02425 else {
02426
02427
02428
02429 if (verbose_ssalv)
02430 trace("Ssalv %.5f _%s_ dropping --- %d %s -> %s [%d]",
02431 Scheduler::instance().clock(),
02432 net_id.dump(), cmh->uid(),
02433 p.src.dump(), p.dest.dump(),
02434 srh->salvaged());
02435 if (mine)
02436 drop(pkt, DROP_RTR_NO_ROUTE);
02437 }
02438 }
02439
02440 #ifdef USE_GOD_FEEDBACK
02441 static int linkerr_is_wrong = 0;
02442 #endif
02443
02444 void
02445 DSRAgent::sendUnknownFlow(SRPacket &p, bool asDefault, u_int16_t flowid) {
02446 hdr_sr *srh = hdr_sr::access(p.pkt);
02447 hdr_ip *iph = hdr_ip::access(p.pkt);
02448 hdr_cmn *cmh = hdr_cmn::access(p.pkt);
02449 struct flow_error *fe;
02450
02451 assert(!srh->num_addrs());
02452 #if 0
02453
02454
02455
02456
02457
02458 assert(p.src != net_id);
02459
02460
02461
02462
02463 assert(srh->flow_header() ^ asDefault);
02464 #endif
02465
02466 if (p.src == net_id) {
02467 Packet::free(p.pkt);
02468 p.pkt = 0;
02469 return;
02470 }
02471
02472 undeliverablePkt(p.pkt, false);
02473
02474
02475 if (asDefault) {
02476 if (!srh->flow_default_unknown()) {
02477 srh->num_default_unknown() = 1;
02478 srh->flow_default_unknown() = 1;
02479 fe = srh->unknown_defaults();
02480 } else if (srh->num_default_unknown() < MAX_ROUTE_ERRORS) {
02481 fe = srh->unknown_defaults() + srh->num_default_unknown();
02482 srh->num_default_unknown()++;
02483 } else {
02484 trace("SYFU %.5f _%s_ dumping maximally nested Flow error %d -> %d",
02485 Scheduler::instance().clock(), net_id.dump(), p.src.addr, p.dest.addr);
02486
02487 Packet::free(p.pkt);
02488 p.pkt = 0;
02489 return;
02490 }
02491 } else {
02492 if (!srh->flow_unknown()) {
02493 srh->num_flow_unknown() = 1;
02494 srh->flow_unknown() = 1;
02495 fe = srh->unknown_flows();
02496 } else if (srh->num_default_unknown() < MAX_ROUTE_ERRORS) {
02497 fe = srh->unknown_flows() + srh->num_flow_unknown();
02498 srh->num_flow_unknown()++;
02499 } else {
02500 trace("SYFU %.5f _%s_ dumping maximally nested Flow error %d -> %d",
02501 Scheduler::instance().clock(), net_id.dump(), p.src.addr, p.dest.addr);
02502
02503 Packet::free(p.pkt);
02504 p.pkt = 0;
02505 return;
02506 }
02507 }
02508
02509 trace("SFErr %.5f _%s_ %d -> %d : %d",
02510 Scheduler::instance().clock(), net_id.dump(), p.src.addr, p.dest.addr,
02511 flowid);
02512
02513 srh->route_reply() = 0;
02514 srh->route_request() = 0;
02515 srh->flow_header() = 0;
02516 srh->flow_timeout() = 0;
02517
02518
02519 iph->daddr() = Address::instance().create_ipaddr(p.src.getNSAddr_t(),RT_PORT);
02520 iph->dport() = RT_PORT;
02521
02522 iph->saddr() = Address::instance().create_ipaddr(net_id.getNSAddr_t(),RT_PORT);
02523 iph->sport() = RT_PORT;
02524 iph->ttl() = 255;
02525
02526
02527 fe->flow_src = p.src.getNSAddr_t();
02528
02529 fe->flow_dst = p.dest.getNSAddr_t();
02530 fe->flow_id = flowid;
02531
02532
02533
02534 p.dest = ID((Address::instance().get_nodeaddr(iph->daddr())),::IP);
02535 p.src = ID((Address::instance().get_nodeaddr(iph->saddr())),::IP);
02536
02537
02538 cmh->ptype() = PT_DSR;
02539 cmh->size() = IP_HDR_LEN;
02540 cmh->num_forwards() = 0;
02541
02542 cmh->uid() = uidcnt_++;
02543
02544 handlePktWithoutSR(p, false);
02545 assert(p.pkt == 0);
02546 }
02547
02548 void
02549 DSRAgent::xmitFlowFailed(Packet *pkt, const char* reason)
02550 {
02551 hdr_sr *srh = hdr_sr::access(pkt);
02552 hdr_ip *iph = hdr_ip::access(pkt);
02553 hdr_cmn *cmh = hdr_cmn::access(pkt);
02554 int flowidx = flow_table.find(iph->saddr(), iph->daddr(), srh->flow_id());
02555 u_int16_t default_flow;
02556
02557 assert(!srh->num_addrs());
02558
02559 if (!srh->flow_header()) {
02560 if (!flow_table.defaultFlow(iph->saddr(), iph->daddr(), default_flow)) {
02561 SRPacket p(pkt, srh);
02562
02563
02564 p.dest = ID((Address::instance().get_nodeaddr(iph->daddr())),::IP);
02565 p.src = ID((Address::instance().get_nodeaddr(iph->saddr())),::IP);
02566
02567
02568 sendUnknownFlow(p, true);
02569 return;
02570 }
02571 flowidx = flow_table.find(iph->saddr(), iph->daddr(), default_flow);
02572 }
02573
02574 if (flowidx == -1 ||
02575 flow_table[flowidx].timeout < Scheduler::instance().clock()) {
02576
02577 SRPacket p(pkt, srh);
02578
02579
02580 p.dest = ID((Address::instance().get_nodeaddr(iph->daddr())),::IP);
02581 p.src = ID((Address::instance().get_nodeaddr(iph->saddr())),::IP);
02582
02583
02584 return;
02585 }
02586
02587 cmh->size() -= srh->size();
02588 assert(cmh->size() >= 0);
02589
02590 flow_table[flowidx].sourceRoute.fillSR(srh);
02591 srh->cur_addr() = flow_table[flowidx].hopCount;
02592 assert(srh->addrs()[srh->cur_addr()].addr == (nsaddr_t) net_id.addr);
02593 cmh->size() += srh->size();
02594
02595
02596 srh->cur_addr()++;
02597 xmitFailed(pkt, reason);
02598 }
02599
02600 void
02601 DSRAgent::xmitFailed(Packet *pkt, const char* reason)
02602
02603
02604
02605
02606 {
02607 hdr_sr *srh = hdr_sr::access(pkt);
02608 hdr_ip *iph = hdr_ip::access(pkt);
02609 hdr_cmn *cmh = hdr_cmn::access(pkt);
02610
02611 assert(cmh->size() >= 0);
02612
02613 srh->cur_addr() -= 1;
02614
02615 if (srh->cur_addr() >= srh->num_addrs() - 1)
02616 {
02617 trace("SDFU: route error beyond end of source route????");
02618 fprintf(stderr,"SDFU: route error beyond end of source route????\n");
02619 Packet::free(pkt);
02620 return;
02621 }
02622
02623 if (srh->route_request())
02624 {
02625 trace("SDFU: route error forwarding route request????");
02626 fprintf(stderr,"SDFU: route error forwarding route request????\n");
02627 Packet::free(pkt);
02628 return;
02629 }
02630
02631
02632 ID tell_id(srh->addrs()[0].addr,
02633 (ID_Type) srh->addrs()[srh->cur_addr()].addr_type);
02634 ID from_id(srh->addrs()[srh->cur_addr()].addr,
02635 (ID_Type) srh->addrs()[srh->cur_addr()].addr_type);
02636 ID to_id(srh->addrs()[srh->cur_addr()+1].addr,
02637 (ID_Type) srh->addrs()[srh->cur_addr()].addr_type);
02638 assert(from_id == net_id || from_id == MAC_id);
02639
02640 trace("SSendFailure %.9f _%s_ %d %d %d:%d %d:%d %s->%s %d %d %d %d %s",
02641 Scheduler::instance().clock(), net_id.dump(),
02642 cmh->uid(), cmh->ptype(),
02643 iph->saddr(), iph->sport(),
02644 iph->daddr(), iph->dport(),
02645 from_id.dump(),to_id.dump(),
02646 God::instance()->hops(from_id.getNSAddr_t(), to_id.getNSAddr_t()),
02647 God::instance()->hops(iph->saddr(),iph->daddr()),
02648 God::instance()->hops(from_id.getNSAddr_t(), iph->daddr()),
02649 srh->num_addrs(), srh->dump());
02650
02651 #ifdef USE_GOD_FEEDBACK
02652 if (God::instance()->hops(from_id.getNSAddr_t(), to_id.getNSAddr_t()) == 1)
02653 {
02654 linkerr_is_wrong++;
02655 trace("SxmitFailed %.5f _%s_ %d->%d god okays #%d",
02656 Scheduler::instance().clock(), net_id.dump(),
02657 from_id.getNSAddr_t(), to_id.getNSAddr_t(), linkerr_is_wrong);
02658 fprintf(stderr,
02659 "xmitFailed on link %d->%d god okays - ignoring & recycling #%d\n",
02660 from_id.getNSAddr_t(), to_id.getNSAddr_t(), linkerr_is_wrong);
02661
02662 srh->cur_addr() += 1;
02663
02664
02665 cmh->direction() = hdr_cmn::DOWN;
02666 ll->recv(pkt, (Handler*) 0);
02667 return;
02668 }
02669 #endif
02670
02671 if(strcmp(reason, "DROP_IFQ_QFULL") != 0) {
02672 assert(strcmp(reason, "DROP_RTR_MAC_CALLBACK") == 0);
02673
02674
02675 route_cache->noticeDeadLink(from_id, to_id,
02676 Scheduler::instance().clock());
02677 flow_table.noticeDeadLink(from_id, to_id);
02678
02679
02680 undeliverablePkt(pkt->copy(), 1);
02681
02682
02683
02684
02685
02686
02687
02688
02689
02690
02691 {
02692 Packet *r, *nr, *queue1 = 0, *queue2 = 0;
02693
02694
02695 while((r = ifq->prq_get_nexthop(to_id.getNSAddr_t()))) {
02696 r->next_ = queue1;
02697 queue1 = r;
02698 }
02699
02700
02701
02702 for(r = queue1; r; r = nr) {
02703 nr = r->next_;
02704 r->next_ = queue2;
02705 queue2 = r;
02706 }
02707
02708
02709 for(r = queue2; r; r = nr) {
02710 nr = r->next_;
02711 undeliverablePkt(r, 1);
02712 }
02713 }
02714 }
02715
02716
02717 if (tell_id == net_id || tell_id == MAC_id)
02718 {
02719 if (verbose)
02720 trace("Sdebug _%s_ not bothering to send route error to ourselves",
02721 tell_id.dump());
02722 Packet::free(pkt);
02723 pkt = 0;
02724 return;
02725 }
02726
02727 if (srh->num_route_errors() >= MAX_ROUTE_ERRORS)
02728 {
02729
02730
02731
02732
02733 trace("SDFU %.5f _%s_ dumping maximally nested error %s %d -> %d",
02734 Scheduler::instance().clock(), net_id.dump(),
02735 tell_id.dump(),
02736 from_id.dump(),
02737 to_id.dump());
02738 Packet::free(pkt);
02739 pkt = 0;
02740 return;
02741 }
02742
02743 link_down *deadlink = &(srh->down_links()[srh->num_route_errors()]);
02744 deadlink->addr_type = srh->addrs()[srh->cur_addr()].addr_type;
02745 deadlink->from_addr = srh->addrs()[srh->cur_addr()].addr;
02746 deadlink->to_addr = srh->addrs()[srh->cur_addr()+1].addr;
02747 deadlink->tell_addr = srh->addrs()[0].addr;
02748 srh->num_route_errors() += 1;
02749
02750 if (verbose)
02751 trace("Sdebug %.5f _%s_ sending into dead-link (nest %d) tell %d %d -> %d",
02752 Scheduler::instance().clock(), net_id.dump(),
02753 srh->num_route_errors(),
02754 deadlink->tell_addr,
02755 deadlink->from_addr,
02756 deadlink->to_addr);
02757
02758 srh->route_error() = 1;
02759 srh->route_reply() = 0;
02760 srh->route_request() = 0;
02761 srh->flow_header() = 0;
02762 srh->flow_timeout() = 0;
02763
02764
02765 iph->daddr() = Address::instance().create_ipaddr(deadlink->tell_addr,RT_PORT);
02766 iph->dport() = RT_PORT;
02767
02768 iph->saddr() = Address::instance().create_ipaddr(net_id.addr,RT_PORT);
02769 iph->sport() = RT_PORT;
02770 iph->ttl() = 255;
02771
02772 cmh->ptype() = PT_DSR;
02773 cmh->size() = IP_HDR_LEN;
02774 cmh->num_forwards() = 0;
02775
02776 cmh->uid() = uidcnt_++;
02777
02778 SRPacket p(pkt, srh);
02779 p.route.setLength(p.route.index()+1);
02780 p.route.reverseInPlace();
02781 p.dest = tell_id;
02782 p.src = net_id;
02783
02784
02785 sendOutPacketWithRoute(p, true);
02786 }
02787
02788 void
02789 XmitFailureCallback(Packet *pkt, void *data)
02790 {
02791 DSRAgent *agent = (DSRAgent *)data;
02792 agent->xmitFailed(pkt);
02793 }
02794
02795 void
02796 XmitFlowFailureCallback(Packet *pkt, void *data)
02797 {
02798 DSRAgent *agent = (DSRAgent *)data;
02799 agent->xmitFlowFailed(pkt);
02800 }
02801
02802 #if 0
02803
02804
02805
02806
02807
02808
02809
02810
02811
02812
02813
02814
02815
02816
02817
02818
02819
02820
02821
02822
02823 struct RtHoldoffData: public EventData {
02824 RtHoldoffData(DSRAgent *th, Packet *pa, int ind):t(th), p(pa), index(ind)
02825 {}
02826 DSRAgent *t;
02827 Packet *p;
02828 int index;
02829 };
02830
02831 void
02832 RouteReplyHoldoffCallback(Node *node, Time time, EventData *data)
02833
02834
02835 {
02836 Packet *p = ((RtHoldoffData *)data)->p;
02837 DSRAgent *t = ((RtHoldoffData *)data)->t;
02838 int index = ((RtHoldoffData *)data)->index;
02839
02840 RtRepHoldoff *entry = &(t->rtrep_holdoff[index]);
02841 assert((entry->requestor == p->dest));
02842
02843
02844
02845 if ((lsnode_require_use && entry->best_length != -1)
02846 || (!lsnode_require_use && entry->best_length > entry->our_length))
02847 {
02848 world_statistics.sendingSrcRtFromCache(t,time,p);
02849 t->sendPacket(t,time,p);
02850 }
02851 else
02852 {
02853 delete p;
02854 }
02855 entry->requestor = invalid_addr;
02856 entry->requested_dest = invalid_addr;
02857 delete data;
02858 t->num_heldoff_rt_replies--;
02859 }
02860
02861 void
02862 DSRAgent::scheduleRouteReply(Time t, Packet *new_p)
02863
02864
02865 {
02866 for (int c = 0; c < RTREP_HOLDOFF_SIZE; c ++)
02867 if (rtrep_holdoff[c].requested_dest == invalid_addr) break;
02868 assert(c < RTREP_HOLDOFF_SIZE);
02869
02870 Path *our_route = &(new_p->data.getRoute().source_route);
02871 rtrep_holdoff[c].requested_dest = (*our_route)[our_route->length() - 1];
02872 rtrep_holdoff[c].requestor = new_p->dest;
02873 rtrep_holdoff[c].best_length = MAX_ROUTE_LEN + 1;
02874 rtrep_holdoff[c].our_length = our_route->length();
02875
02876 Time send_time = t +
02877 (Time) (our_route->length() - 1) * rt_rep_holdoff_period
02878 + U(0.0, rt_rep_holdoff_period);
02879 RegisterCallback(this,&RouteReplyHoldoffCallback, send_time,
02880 new RtHoldoffData(this,new_p,c));
02881 num_heldoff_rt_replies++;
02882 }
02883
02884 void
02885 DSRAgent::snoopForRouteReplies(Time t, Packet *p)
02886
02887
02888 {
02889 for (int c = 0 ; c <RTREP_HOLDOFF_SIZE ; c ++)
02890 {
02891 RtRepHoldoff *entry = &(rtrep_holdoff[c]);
02892
02893
02894
02895
02896 if (entry->requestor == p->dest
02897 && (p->type == ::route_reply || p->data.sourceRoutep()))
02898 {
02899 Path *srcrt = &(p->data.getRoute().source_route);
02900 if (!(entry->requested_dest == (*srcrt)[srcrt->length()-1]))
02901 continue;
02902 if (entry->best_length > srcrt->length())
02903 entry->best_length = srcrt->length();
02904 }
02905 else if (entry->requestor == p->src
02906 && entry->requested_dest == p->dest)
02907 {
02908 if (p->route.length() <= entry->our_length)
02909 {
02910 entry->best_length = -1;
02911 }
02912 }
02913 else
02914 continue;
02915 }
02916 }
02917
02918 #endif //0
02919
02920
02921
02922
02923
02924
02925
02926