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 #include "rtmodule.h"
00051 #include <assert.h>
00052 #include "node.h"
00053
00054
00055 static class RoutingModuleClass : public TclClass {
00056 public:
00057 RoutingModuleClass() : TclClass("RtModule") {}
00058 TclObject* create(int, const char*const*) {
00059 return (new RoutingModule);
00060 }
00061 } class_routing_module;
00062
00063 static class BaseRoutingModuleClass : public TclClass {
00064 public:
00065 BaseRoutingModuleClass() : TclClass("RtModule/Base") {}
00066 TclObject* create(int, const char*const*) {
00067 return (new BaseRoutingModule);
00068 }
00069 } class_base_routing_module;
00070
00071 static class McastRoutingModuleClass : public TclClass {
00072 public:
00073 McastRoutingModuleClass() : TclClass("RtModule/Mcast") {}
00074 TclObject* create(int, const char*const*) {
00075 return (new McastRoutingModule);
00076 }
00077 } class_mcast_routing_module;
00078
00079 static class HierRoutingModuleClass : public TclClass {
00080 public:
00081 HierRoutingModuleClass() : TclClass("RtModule/Hier") {}
00082 TclObject* create(int, const char*const*) {
00083 return (new HierRoutingModule);
00084 }
00085 } class_hier_routing_module;
00086
00087
00088 static class ManualRoutingModuleClass : public TclClass {
00089 public:
00090 ManualRoutingModuleClass() : TclClass("RtModule/Manual") {}
00091 TclObject* create(int, const char*const*) {
00092 return (new ManualRoutingModule);
00093 }
00094 } class_manual_routing_module;
00095
00096 static class SourceRoutingModuleClass : public TclClass {
00097 public:
00098 SourceRoutingModuleClass() : TclClass("RtModule/Source") {}
00099 TclObject* create(int, const char*const*) {
00100 return (new SourceRoutingModule);
00101 }
00102 } class_source_routing_module;
00103
00104 static class QSRoutingModuleClass : public TclClass {
00105 public:
00106 QSRoutingModuleClass() : TclClass("RtModule/QS") {}
00107 TclObject* create(int, const char*const*) {
00108 return (new QSRoutingModule);
00109 }
00110 } class_qs_routing_module;
00111
00112 static class VcRoutingModuleClass : public TclClass {
00113 public:
00114 VcRoutingModuleClass() : TclClass("RtModule/VC") {}
00115 TclObject* create(int, const char*const*) {
00116 return (new VcRoutingModule);
00117 }
00118 } class_vc_routing_module;
00119
00120
00121 #ifdef HAVE_STL
00122 static class PgmRoutingModuleClass : public TclClass {
00123 public:
00124 PgmRoutingModuleClass() : TclClass("RtModule/PGM") {}
00125 TclObject* create(int, const char*const*) {
00126 return (new PgmRoutingModule);
00127 }
00128 } class_pgm_routing_module;
00129 #endif //STL
00130
00131
00132 static class LmsRoutingModuleClass : public TclClass {
00133 public:
00134 LmsRoutingModuleClass() : TclClass("RtModule/LMS") {}
00135 TclObject* create(int, const char*const*) {
00136 return (new LmsRoutingModule);
00137 }
00138 } class_lms_routing_module;
00139
00140 RoutingModule::RoutingModule() :
00141 next_rtm_(NULL), n_(NULL), classifier_(NULL) {
00142 bind("classifier_", (TclObject**)&classifier_);
00143 }
00144
00145 int RoutingModule::command(int argc, const char*const* argv)
00146 {
00147 Tcl& tcl = Tcl::instance();
00148 if (argc == 2) {
00149 if (strcmp(argv[1], "node") == 0) {
00150 assert(n_ != NULL);
00151 tcl.resultf("%s", n_->name());
00152 return TCL_OK;
00153 } else if (strcmp(argv[1], "module-name") == 0) {
00154 if (module_name() != NULL)
00155 tcl.resultf("%s", module_name());
00156 else
00157 tcl.result("");
00158 return TCL_OK;
00159 }
00160
00161 } else if (argc == 3) {
00162 if (strcmp(argv[1], "attach-node") == 0) {
00163 n_ = (Node*)TclObject::lookup(argv[2]);
00164 if (n_ == NULL) {
00165 tcl.add_errorf("Wrong object name %s",argv[2]);
00166 return TCL_ERROR;
00167 }
00168 return TCL_OK;
00169 }
00170
00171
00172
00173
00174
00175
00176
00177
00178 }
00179 return TclObject::command(argc, argv);
00180 }
00181
00182 int BaseRoutingModule::command(int argc, const char*const* argv) {
00183 Tcl& tcl = Tcl::instance();
00184 if (argc == 3) {
00185 if (strcmp(argv[1] , "route-notify") == 0) {
00186 Node *node = (Node *)(TclObject::lookup(argv[2]));
00187 if (node == NULL) {
00188 tcl.add_errorf("Invalid node object %s", argv[2]);
00189 return TCL_ERROR;
00190 }
00191 if (node != n_) {
00192 tcl.add_errorf("Node object %s different from n_", argv[2]);
00193 return TCL_ERROR;
00194 }
00195 n_->route_notify(this);
00196 return TCL_OK;
00197 }
00198 if (strcmp(argv[1] , "unreg-route-notify") == 0) {
00199 Node *node = (Node *)(TclObject::lookup(argv[2]));
00200 if (node == NULL) {
00201 tcl.add_errorf("Invalid node object %s", argv[2]);
00202 return TCL_ERROR;
00203 }
00204 if (node != n_) {
00205 tcl.add_errorf("Node object %s different from n_", argv[2]);
00206 return TCL_ERROR;
00207 }
00208 n_->unreg_route_notify(this);
00209 return TCL_OK;
00210 }
00211 }
00212 return (RoutingModule::command(argc, argv));
00213 }
00214
00215 int SourceRoutingModule::command(int argc, const char*const* argv) {
00216 Tcl& tcl = Tcl::instance();
00217 if (argc == 3) {
00218 if (strcmp(argv[1] , "route-notify") == 0) {
00219 Node *node = (Node *)(TclObject::lookup(argv[2]));
00220 if (node == NULL) {
00221 tcl.add_errorf("Invalid node object %s", argv[2]);
00222 return TCL_ERROR;
00223 }
00224 if (node != n_) {
00225 tcl.add_errorf("Node object %s different from n_", argv[2]);
00226 return TCL_ERROR;
00227 }
00228 n_->route_notify(this);
00229 return TCL_OK;
00230 }
00231 if (strcmp(argv[1] , "unreg-route-notify") == 0) {
00232 Node *node = (Node *)(TclObject::lookup(argv[2]));
00233 if (node == NULL) {
00234 tcl.add_errorf("Invalid node object %s", argv[2]);
00235 return TCL_ERROR;
00236 }
00237 if (node != n_) {
00238 tcl.add_errorf("Node object %s different from n_", argv[2]);
00239 return TCL_ERROR;
00240 }
00241 n_->unreg_route_notify(this);
00242 return TCL_OK;
00243 }
00244 }
00245 return (RoutingModule::command(argc, argv));
00246 }
00247
00248 int QSRoutingModule::command(int argc, const char*const* argv) {
00249 Tcl& tcl = Tcl::instance();
00250 if (argc == 3) {
00251 if (strcmp(argv[1] , "route-notify") == 0) {
00252 Node *node = (Node *)(TclObject::lookup(argv[2]));
00253 if (node == NULL) {
00254 tcl.add_errorf("Invalid node object %s", argv[2]);
00255 return TCL_ERROR;
00256 }
00257 if (node != n_) {
00258 tcl.add_errorf("Node object %s different from n_", argv[2]);
00259 return TCL_ERROR;
00260 }
00261 n_->route_notify(this);
00262 return TCL_OK;
00263 }
00264 if (strcmp(argv[1] , "unreg-route-notify") == 0) {
00265 Node *node = (Node *)(TclObject::lookup(argv[2]));
00266 if (node == NULL) {
00267 tcl.add_errorf("Invalid node object %s", argv[2]);
00268 return TCL_ERROR;
00269 }
00270 if (node != n_) {
00271 tcl.add_errorf("Node object %s different from n_", argv[2]);
00272 return TCL_ERROR;
00273 }
00274 n_->unreg_route_notify(this);
00275 return TCL_OK;
00276 }
00277 }
00278 return (RoutingModule::command(argc, argv));
00279 }
00280
00281 int McastRoutingModule::command(int argc, const char*const* argv) {
00282 Tcl& tcl = Tcl::instance();
00283 if (argc == 3) {
00284 if (strcmp(argv[1] , "route-notify") == 0) {
00285 Node *node = (Node *)(TclObject::lookup(argv[2]));
00286 if (node == NULL) {
00287 tcl.add_errorf("Invalid node object %s", argv[2]);
00288 return TCL_ERROR;
00289 }
00290 if (node != n_) {
00291 tcl.add_errorf("Node object %s different from n_", argv[2]);
00292 return TCL_ERROR;
00293 }
00294 n_->route_notify(this);
00295 return TCL_OK;
00296 }
00297 if (strcmp(argv[1] , "unreg-route-notify") == 0) {
00298 Node *node = (Node *)(TclObject::lookup(argv[2]));
00299 if (node == NULL) {
00300 tcl.add_errorf("Invalid node object %s", argv[2]);
00301 return TCL_ERROR;
00302 }
00303 if (node != n_) {
00304 tcl.add_errorf("Node object %s different from n_", argv[2]);
00305 return TCL_ERROR;
00306 }
00307 n_->unreg_route_notify(this);
00308 return TCL_OK;
00309 }
00310 }
00311 return (RoutingModule::command(argc, argv));
00312 }
00313
00314 int HierRoutingModule::command(int argc, const char*const* argv) {
00315 Tcl& tcl = Tcl::instance();
00316 if (argc == 3) {
00317
00318
00319
00320
00321
00322
00323
00324
00325 if (strcmp(argv[1] , "route-notify") == 0) {
00326 Node *node = (Node *)(TclObject::lookup(argv[2]));
00327 if (node == NULL) {
00328 tcl.add_errorf("Invalid node object %s", argv[2]);
00329 return TCL_ERROR;
00330 }
00331 if (node != n_) {
00332 tcl.add_errorf("Node object %s different from n_", argv[2]);
00333 return TCL_ERROR;
00334 }
00335 n_->route_notify(this);
00336 return TCL_OK;
00337 }
00338 if (strcmp(argv[1] , "unreg-route-notify") == 0) {
00339 Node *node = (Node *)(TclObject::lookup(argv[2]));
00340 if (node == NULL) {
00341 tcl.add_errorf("Invalid node object %s", argv[2]);
00342 return TCL_ERROR;
00343 }
00344 if (node != n_) {
00345 tcl.add_errorf("Node object %s different from n_", argv[2]);
00346 return TCL_ERROR;
00347 }
00348 n_->unreg_route_notify(this);
00349 return TCL_OK;
00350 }
00351 }
00352 return (RoutingModule::command(argc, argv));
00353 }
00354
00355
00356 int ManualRoutingModule::command(int argc, const char*const* argv) {
00357 Tcl& tcl = Tcl::instance();
00358 if (argc == 3) {
00359 if (strcmp(argv[1] , "route-notify") == 0) {
00360 Node *node = (Node *)(TclObject::lookup(argv[2]));
00361 if (node == NULL) {
00362 tcl.add_errorf("Invalid node object %s", argv[2]);
00363 return TCL_ERROR;
00364 }
00365 if (node != n_) {
00366 tcl.add_errorf("Node object %s different from node_", argv[2]);
00367 return TCL_ERROR;
00368 }
00369 n_->route_notify(this);
00370 return TCL_OK;
00371 }
00372 if (strcmp(argv[1] , "unreg-route-notify") == 0) {
00373 Node *node = (Node *)(TclObject::lookup(argv[2]));
00374 if (node == NULL) {
00375 tcl.add_errorf("Invalid node object %s", argv[2]);
00376 return TCL_ERROR;
00377 }
00378 if (node != n_) {
00379 tcl.add_errorf("Node object %s different from n_", argv[2]);
00380 return TCL_ERROR;
00381 }
00382 n_->unreg_route_notify(this);
00383 return TCL_OK;
00384 }
00385 }
00386 return (RoutingModule::command(argc, argv));
00387 }
00388
00389 void VcRoutingModule::add_route(char *, NsObject *) { }
00390
00391
00392 int VcRoutingModule::command(int argc, const char*const* argv) {
00393 Tcl& tcl = Tcl::instance();
00394 if (argc == 3) {
00395 if (strcmp(argv[1] , "route-notify") == 0) {
00396 Node *node = (Node *)(TclObject::lookup(argv[2]));
00397 if (node == NULL) {
00398 tcl.add_errorf("Invalid node object %s", argv[2]);
00399 return TCL_ERROR;
00400 }
00401 if (node != n_) {
00402 tcl.add_errorf("Node object %s different from n_", argv[2]);
00403 return TCL_ERROR;
00404 }
00405 n_->route_notify(this);
00406 return TCL_OK;
00407 }
00408 if (strcmp(argv[1] , "unreg-route-notify") == 0) {
00409 Node *node = (Node *)(TclObject::lookup(argv[2]));
00410 if (node == NULL) {
00411 tcl.add_errorf("Invalid node object %s", argv[2]);
00412 return TCL_ERROR;
00413 }
00414 if (node != n_) {
00415 tcl.add_errorf("Node object %s different from n_", argv[2]);
00416 return TCL_ERROR;
00417 }
00418 n_->unreg_route_notify(this);
00419 return TCL_OK;
00420 }
00421 }
00422 return (RoutingModule::command(argc, argv));
00423 }
00424
00425 void RoutingModule::route_notify(RoutingModule *rtm) {
00426 if (next_rtm_ != NULL)
00427 next_rtm_->route_notify(rtm);
00428 else
00429 next_rtm_ = rtm;
00430 }
00431
00432 void RoutingModule::unreg_route_notify(RoutingModule *rtm) {
00433 if (next_rtm_) {
00434 if (next_rtm_ == rtm) {
00435
00436 next_rtm_ = next_rtm_->next_rtm_;
00437
00438 }
00439 else {
00440 next_rtm_->unreg_route_notify(rtm);
00441 }
00442 }
00443 }
00444
00445 void RoutingModule::add_route(char *dst, NsObject *target)
00446 {
00447 if (classifier_)
00448 classifier_->do_install(dst,target);
00449 if (next_rtm_ != NULL)
00450 next_rtm_->add_route(dst, target);
00451 }
00452
00453 void RoutingModule::delete_route(char *dst, NsObject *nullagent)
00454 {
00455 if (classifier_)
00456 classifier_->do_install(dst, nullagent);
00457 if (next_rtm_)
00458 next_rtm_->add_route(dst, nullagent);
00459 }
00460
00461 void RoutingModule::set_table_size(int nn)
00462 {
00463 if (classifier_)
00464 classifier_->set_table_size(nn);
00465 if (next_rtm_)
00466 next_rtm_->set_table_size(nn);
00467 }
00468
00469 void RoutingModule::set_table_size(int level, int size)
00470 {
00471 if (classifier_)
00472 classifier_->set_table_size(level, size);
00473 if (next_rtm_)
00474 next_rtm_->set_table_size(level, size);
00475 }
00476
00477
00478
00479
00480
00481
00482
00483
00484
00485
00486
00487
00488
00489
00490
00491
00492
00493
00494
00495
00496
00497
00498 void ManualRoutingModule::add_route(char *dst, NsObject *target) {
00499 int slot = classifier_->install_next(target);
00500 if (strcmp(dst, "default") == 0) {
00501 classifier_->set_default(slot);
00502 } else {
00503 int encoded_dst_address =
00504 (atoi(dst)) << (AddrParamsClass::instance().node_shift(1));
00505 if (0 > (classifier_->do_set_hash(0, encoded_dst_address, 0, slot))) {
00506 fprintf(stderr, "HashClassifier::set_hash() return value less than 0\n"); }
00507 }
00508 if (next_rtm_ != NULL)
00509 next_rtm_->add_route(dst, target);
00510 }
00511