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 #include <template.h>
00049 #include <gaf/gaf.h>
00050 #include <random.h>
00051 #include <address.h>
00052 #include <mobilenode.h>
00053 #include <god.h>
00054 #include <phy.h>
00055 #include <wireless-phy.h>
00056 #include <energy-model.h>
00057
00058
00059
00060 int hdr_gaf::offset_;
00061 static class GAFHeaderClass : public PacketHeaderClass {
00062 public:
00063 GAFHeaderClass() : PacketHeaderClass("PacketHeader/GAF",
00064 sizeof(hdr_gaf)) {
00065 bind_offset(&hdr_gaf::offset_);
00066 }
00067 } class_gafhdr;
00068
00069 static class GAFAgentClass : public TclClass {
00070 public:
00071 GAFAgentClass() : TclClass("Agent/GAF") {}
00072 TclObject* create(int argc, const char*const* argv) {
00073 assert(argc == 5);
00074 return (new GAFAgent((nsaddr_t) atoi(argv[4])));
00075 }
00076 } class_gafagent;
00077
00078 static class GAFPartnerClass : public TclClass {
00079 public:
00080 GAFPartnerClass() : TclClass("GAFPartner") {}
00081 TclObject* create(int, const char*const*) {
00082 return (new GAFPartner());
00083 }
00084 } class_gafparnter;
00085
00086
00087 static inline double
00088 gafjitter (double max, int be_random_)
00089 {
00090 return (be_random_ ? Random::uniform(max) : max);
00091 }
00092
00093
00094 GAFAgent::GAFAgent(nsaddr_t id) : Agent(PT_GAF), beacon_(1), randomflag_(1), timer_(this), stimer_(this), dtimer_(this), maxttl_(5), state_(GAF_FREE),leader_settime_(0),adapt_mobility_(0)
00095 {
00096 double x = 0.0, y = 0.0, z = 0.0;
00097
00098 seqno_ = -1;
00099 nid_ = id;
00100 thisnode = Node::get_node_by_address(nid_);
00101
00102
00103
00104
00105
00106 ((MobileNode *)thisnode)->getLoc(&x, &y, &z);
00107 gid_ = God::instance()->getMyGrid(x,y);
00108
00109 if (gid_ < 0) {
00110 printf("fatal error: node is outside topography\n");
00111 }
00112 }
00113
00114 void GAFAgent::recv(Packet* p, Handler *)
00115 {
00116 hdr_gaf *gafh = hdr_gaf::access(p);
00117
00118 switch (gafh->type_) {
00119
00120 case GAF_DISCOVER:
00121
00122 if (state_ != GAF_SLEEP)
00123 processDiscoveryMsg(p);
00124 Packet::free(p);
00125 break;
00126
00127 default:
00128 Packet::free(p);
00129 break;
00130 }
00131 }
00132
00133
00134 void GAFAgent::processDiscoveryMsg(Packet* p)
00135 {
00136 struct DiscoveryMsg emsg;
00137 u_int32_t dst;
00138 unsigned char *w = p->accessdata ();
00139 double x = 0.0, y = 0.0, z = 0.0;
00140 int ttl;
00141
00142
00143 dst = *(w++);
00144 dst = dst << 8 | *(w++);
00145 dst = dst << 8 | *(w++);
00146 dst = dst << 8 | *(w++);
00147
00148 emsg.gid = dst;
00149
00150 dst = *(w++);
00151 dst = dst << 8 | *(w++);
00152 dst = dst << 8 | *(w++);
00153 dst = dst << 8 | *(w++);
00154
00155 emsg.nid = dst;
00156
00157 dst = *(w++);
00158 dst = dst << 8 | *(w++);
00159 dst = dst << 8 | *(w++);
00160 dst = dst << 8 | *(w++);
00161
00162 emsg.state = dst;
00163
00164 dst = *(w++);
00165 dst = dst << 8 | *(w++);
00166 dst = dst << 8 | *(w++);
00167 dst = dst << 8 | *(w++);
00168
00169 emsg.ttl = dst;
00170
00171 dst = *(w++);
00172 dst = dst << 8 | *(w++);
00173 dst = dst << 8 | *(w++);
00174 dst = dst << 8 | *(w++);
00175
00176 emsg.stime = dst;
00177
00178
00179
00180 ((MobileNode *)thisnode)->getLoc(&x, &y, &z);
00181 gid_ = God::instance()->getMyGrid(x,y);
00182
00183
00184 if (((u_int32_t)gid_) != (u_int32_t)emsg.gid) return;
00185
00186
00187 switch (emsg.state) {
00188
00189 case GAF_LEADER:
00190
00191
00192
00193
00194
00195 switch (state_) {
00196 case GAF_LEADER:
00197
00198 ttl = (int)(leader_settime_ - NOW);
00199 if (ttl < 0) ttl = 0;
00200
00201 if ( ((u_int32_t)ttl) > (u_int32_t) emsg.ttl) {
00202
00203 send_discovery();
00204 return;
00205
00206 } else {
00207 if (((u_int32_t)ttl) == emsg.ttl && (u_int32_t)nid_ < emsg.nid) {
00208 send_discovery();
00209 return;
00210 }
00211
00212 stimer_.force_cancel();
00213 leader_settime_ = 0;
00214
00215
00216 schedule_wakeup(emsg);
00217 }
00218
00219 break;
00220
00221 case GAF_FREE:
00222 schedule_wakeup(emsg);
00223
00224 break;
00225 default:
00226 break;
00227
00228 }
00229
00230 break;
00231 case GAF_FREE:
00232 if (state_ == GAF_FREE) {
00233 if ((ttl = (int)myttl()) > MIN_LIFETIME) {
00234 ttl = ttl/2;
00235 }
00236
00237 if ( ttl > (int)emsg.ttl) {
00238
00239 send_discovery();
00240 return;
00241 } else {
00242 if ((u_int32_t)ttl == emsg.ttl && (u_int32_t)nid_ < emsg.nid) {
00243 send_discovery();
00244 return;
00245 }
00246
00247 schedule_wakeup(emsg);
00248
00249 }
00250 }
00251
00252 if (state_ == GAF_LEADER) {
00253 send_discovery();
00254 }
00255
00256 break;
00257 default:
00258 printf("%d gets wrong discovery msg\n",nid_ );;
00259 break;
00260 }
00261
00262 }
00263
00264 void GAFAgent::schedule_wakeup(struct DiscoveryMsg emsg) {
00265
00266 int waketime;
00267 waketime = emsg.ttl;
00268
00269
00270 if (adapt_mobility_ > 0 ) {
00271 if (emsg.stime < emsg.ttl) waketime = emsg.stime;
00272 }
00273
00274
00275
00276
00277 if (waketime > MIN_TURNOFFTIME ) {
00278 node_off();
00279 dtimer_.resched(Random::uniform(waketime/2, waketime));
00280 }
00281 }
00282
00283 double GAFAgent::myttl()
00284 {
00285 double ce,maxp;
00286 Phy *phyp;
00287 double ttl;
00288
00289 ce = (thisnode->energy_model())->energy();
00290
00291 phyp = (thisnode->ifhead()).lh_first;
00292
00293 assert (phyp != 0);
00294 maxp = ((WirelessPhy *)phyp)->getPtconsume();
00295 ttl = ce/maxp;
00296
00297 return ttl;
00298
00299 }
00300
00301
00302 void GAFAgent::timeout(GafMsgType msgt)
00303 {
00304
00305 int ttl;
00306
00307
00308
00309 switch (msgt) {
00310 case GAF_DISCOVER:
00311
00312 switch (state_) {
00313 case GAF_SLEEP:
00314 break;
00315
00316 case GAF_FREE:
00317
00318 if ((ttl = (int)myttl()) > MIN_LIFETIME) {
00319 ttl = (int) ttl/2;
00320 }
00321
00322 leader_settime_ = (int) (ttl + NOW);
00323
00324
00325
00326 stimer_.resched(ttl);
00327
00328 setGAFstate(GAF_LEADER);
00329
00330 send_discovery();
00331
00332
00333
00334 timer_.resched(Random::uniform(MAX_DISCOVERY_TIME-1,MAX_DISCOVERY_TIME));
00335
00336
00337 break;
00338
00339 case GAF_LEADER:
00340
00341 send_discovery();
00342
00343 timer_.resched(Random::uniform(MAX_DISCOVERY_TIME-1,MAX_DISCOVERY_TIME));
00344 break;
00345 default:
00346 break;
00347
00348 }
00349
00350 break;
00351
00352 case GAF_SELECT:
00353 switch (state_) {
00354
00355 case GAF_LEADER:
00356
00357
00358
00359
00360
00361
00362
00363 duty_timeout();
00364
00365 leader_settime_ = 0;
00366
00367 break;
00368
00369 case GAF_FREE:
00370 case GAF_SLEEP:
00371 break;
00372 default:
00373 break;
00374 }
00375 break;
00376 case GAF_DUTY:
00377 duty_timeout();
00378 break;
00379 default:
00380 printf("Wrong GAF msg time!\n");
00381 }
00382
00383 }
00384
00385
00386
00387 void GAFAgent::duty_timeout()
00388 {
00389 double x=0.0, y=0.0, z=0.0;
00390
00391
00392
00393 ((MobileNode *)thisnode)->getLoc(&x, &y, &z);
00394 gid_ = God::instance()->getMyGrid(x,y);
00395
00396
00397
00398 node_on();
00399
00400
00401
00402
00403 send_discovery();
00404
00405
00406
00407
00408 timer_.resched(gafjitter(GAF_NONSTART_JITTER, 1));
00409
00410 }
00411
00412 int GAFAgent::command(int argc, const char*const* argv)
00413 {
00414 if (argc == 2) {
00415 if (strcmp (argv[1], "start-gaf") == 0) {
00416
00417 timer_.resched(gafjitter(GAF_STARTUP_JITTER, 1));
00418
00419
00420
00421
00422 return (TCL_OK);
00423 }
00424
00425 }
00426 if (argc == 3) {
00427 if (strcmp(argv[1], "adapt-mobility") == 0) {
00428 adapt_mobility_ = atoi(argv[2]);
00429
00430 return TCL_OK;
00431 }
00432
00433 if (strcmp(argv[1], "maxttl") == 0) {
00434 maxttl_ = atoi(argv[2]);
00435 return TCL_OK;
00436 }
00437
00438 }
00439 return (Agent::command(argc, argv));
00440 }
00441
00442 void GAFAgent::send_discovery()
00443 {
00444 Packet *p = allocpkt();
00445 double x=0.0, y=0.0, z=0.0;
00446
00447 hdr_gaf *h = hdr_gaf::access(p);
00448
00449
00450 h->type_ = GAF_DISCOVER;
00451 h->seqno_ = ++seqno_;
00452
00453
00454
00455 ((MobileNode *)thisnode)->getLoc(&x, &y, &z);
00456 gid_ = God::instance()->getMyGrid(x,y);
00457
00458 makeUpDiscoveryMsg(p);
00459
00460 send(p,0);
00461 }
00462
00463 void
00464 GAFAgent::makeUpDiscoveryMsg(Packet *p)
00465 {
00466 hdr_ip *iph = hdr_ip::access(p);
00467 hdr_cmn *hdrc = hdr_cmn::access(p);
00468 u_int32_t ttl,stime;
00469 unsigned char *walk;
00470 double gridsize, speed;
00471
00472
00473 hdrc->next_hop_ = IP_BROADCAST;
00474 hdrc->addr_type_ = NS_AF_INET;
00475 iph->daddr() = IP_BROADCAST << Address::instance().nodeshift();
00476 iph->dport() = 254;
00477
00478
00479
00480
00481
00482 p->allocdata(sizeof(DiscoveryMsg));
00483 walk = p->accessdata ();
00484 hdrc->size_ = sizeof(DiscoveryMsg) + IP_HDR_LEN;
00485
00486 *(walk++) = gid_ >> 24;
00487 *(walk++) = (gid_ >> 16) & 0xFF;
00488 *(walk++) = (gid_ >> 8) & 0xFF;
00489 *(walk++) = (gid_ >> 0) & 0xFF;
00490 *(walk++) = nid_ >> 24;
00491 *(walk++) = (nid_ >> 16) & 0xFF;
00492 *(walk++) = (nid_ >> 8) & 0xFF;
00493 *(walk++) = (nid_ >> 0) & 0xFF;
00494
00495
00496
00497 *(walk++) = state_ >> 24;
00498 *(walk++) = (state_ >> 16) & 0xFF;
00499 *(walk++) = (state_ >> 8) & 0xFF;
00500 *(walk++) = (state_ >> 0) & 0xFF;
00501
00502
00503
00504
00505
00506 if (state_ == GAF_LEADER) {
00507
00508 ttl = (int)(leader_settime_ - NOW);
00509 if (ttl < 0) ttl = 0;
00510
00511 } else {
00512
00513 if ((ttl = (u_int32_t)myttl()) > MIN_LIFETIME) {
00514 ttl = (u_int32_t) ttl/2;
00515 }
00516
00517 }
00518 *(walk++) = ttl >> 24;
00519 *(walk++) = (ttl >> 16) & 0xFF;
00520 *(walk++) = (ttl >> 8) & 0xFF;
00521 *(walk++) = (ttl >> 0) & 0xFF;
00522
00523
00524
00525
00526
00527 speed = ((MobileNode*)thisnode)->speed();
00528
00529 if (speed == 0) {
00530
00531 stime = 2*ttl;
00532 } else {
00533 gridsize = God::instance()->getMyGridSize();
00534 stime = (u_int32_t) (gridsize/speed);
00535 }
00536
00537 *(walk++) = stime >> 24;
00538 *(walk++) = (stime >> 16) & 0xFF;
00539 *(walk++) = (stime >> 8) & 0xFF;
00540 *(walk++) = (stime >> 0) & 0xFF;
00541
00542
00543
00544 }
00545
00546
00547 void
00548 GAFAgent::node_off()
00549 {
00550 Phy *p;
00551 EnergyModel *em;
00552
00553
00554
00555
00556
00557
00558
00559
00560
00561 em = thisnode->energy_model();
00562 em->node_on() = false;
00563
00564
00565
00566 p = (thisnode->ifhead()).lh_first;
00567 if (p) {
00568 ((WirelessPhy *)p)->node_off();
00569 }
00570
00571 setGAFstate(GAF_SLEEP);
00572 }
00573
00574 void
00575 GAFAgent::node_on()
00576 {
00577 Phy *p;
00578 EnergyModel* em;
00579
00580
00581
00582 em = thisnode->energy_model();
00583 em->node_on() = true;
00584
00585
00586
00587
00588
00589 p = (thisnode->ifhead()).lh_first;
00590 if (p) {
00591 ((WirelessPhy *)p)->node_on();
00592 }
00593
00594 setGAFstate(GAF_FREE);
00595 }
00596
00597 void
00598 GAFAgent::setGAFstate(GafNodeState gs)
00599 {
00600
00601
00602 state_ = gs;
00603 }
00604
00605 GAFPartner::GAFPartner() : Connector(), gafagent_(1),mask_(0xffffffff),
00606 shift_(8)
00607 {
00608 bind("addr_", (int*)&(here_.addr_));
00609 bind("port_", (int*)&(here_.port_));
00610 bind("shift_", &shift_);
00611 bind("mask_", &mask_);
00612 }
00613
00614 void GAFPartner::recv(Packet* p, Handler *h)
00615 {
00616 hdr_ip* hdr = hdr_ip::access(p);
00617 hdr_cmn *hdrc = hdr_cmn::access(p);
00618
00619
00620
00621
00622 if ( hdrc->ptype() == PT_GAF ) {
00623 if (gafagent_ == 1) {
00624 if (((u_int32_t)hdr->daddr()) == IP_BROADCAST) {
00625 hdr->daddr() = here_.addr_;
00626 }
00627 } else {
00628
00629 drop (p);
00630 return;
00631 }
00632 }
00633
00634 target_->recv(p,h);
00635
00636
00637 }
00638
00639 int GAFPartner::command(int argc, const char*const* argv)
00640 {
00641 if (argc == 3) {
00642 if (strcmp (argv[1], "set-gafagent") == 0) {
00643 gafagent_ = atoi(argv[2]);
00644 return (TCL_OK);
00645 }
00646 }
00647 return Connector::command(argc, argv);
00648 }
00649
00650 void GAFDiscoverTimer::expire(Event *) {
00651 a_->timeout(GAF_DISCOVER);
00652 }
00653
00654 void GAFSelectTimer::expire(Event *) {
00655 a_->timeout(GAF_SELECT);
00656 }
00657
00658 void GAFDutyTimer::expire(Event *) {
00659 a_->timeout(GAF_DUTY);
00660 }
00661
00662
00663
00664