module.cc

00001 /*
00002  * Copyright (c) 2006 Regents of the SIGNET lab, University of Padova.
00003  * All rights reserved.
00004  *
00005  * Redistribution and use in source and binary forms, with or without
00006  * modification, are permitted provided that the following conditions
00007  * are met:
00008  * 1. Redistributions of source code must retain the above copyright
00009  *    notice, this list of conditions and the following disclaimer.
00010  * 2. Redistributions in binary form must reproduce the above copyright
00011  *    notice, this list of conditions and the following disclaimer in the
00012  *    documentation and/or other materials provided with the distribution.
00013  * 3. Neither the name of the University of Padova (SIGNET lab) nor the 
00014  *    names of its contributors may be used to endorse or promote products 
00015  *    derived from this software without specific prior written permission.
00016  *
00017  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 
00018  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 
00019  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 
00020  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 
00021  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 
00022  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 
00023  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 
00024  * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 
00025  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 
00026  * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 
00027  * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00028  */
00029  
00030 
00031 #include <string.h>
00032 #include "module.h"
00033 #include "deprecated.h"
00034 
00035 
00036 /* ======================================================================
00037    TCL Hooks for the simulator
00038    ====================================================================== */
00039 // static class ModuleClass : public TclClass {
00040 // public:
00041 //      ModuleClass() : TclClass("Module") {}
00042 //      TclObject* create(int, const char*const*) {
00043 //              return (new Module());
00044 //      }
00045 // } class_module;
00046 
00047 Module::Module() : upLayerSAP_(0),upLaySAPnum_(0), downLayerSAP_(0), downLaySAPnum_(0)
00048 {
00049         // variables could be bound: no one...
00050 }
00051 
00052 Module::~Module()
00053 {
00054 }
00055 
00056 // // TCL command intepreter
00057 int Module::command(int argc, const char* const* argv)
00058 {
00059         Tcl& tcl = Tcl::instance();
00060         if (argc==3)
00061         {
00062                 // install a SAP to an above module
00063                 if (strcasecmp(argv[1],"addupsap")==0)
00064                 {
00065                          SAP *sap = dynamic_cast<SAP*>(TclObject::lookup(argv[2]));
00066                         addUpSAP(sap);
00067                         if(debug_ > 5)
00068                                 printf("addUpsap\n");
00069                         return (TCL_OK);
00070                 }
00071                 // install a SAP to a bottom module
00072                 if (strcasecmp(argv[1],"adddownsap")==0)
00073                 {
00074                         SAP *sap = dynamic_cast<SAP*>(TclObject::lookup(argv[2]));
00075                         addDownSAP(sap);
00076                         if(debug_ > 5)
00077                                 printf("addDownsap\n");
00078                         return (TCL_OK);
00079                 }
00080                 if (strcasecmp(argv[1],"setlayer")==0)
00081                 {
00082                         int val = atoi(argv[2]);
00083                         setLayer(val);
00084                         return TCL_OK;
00085                 }
00086         }
00087         return PlugIn::command(argc, argv);
00088 }
00089 
00090 int Module::getUpLaySAPnum()
00091 {
00092         return(upLaySAPnum_);
00093 }
00094 
00095 SAP* Module::getUpLaySAP(int i)
00096 {
00097         if (i<0 || i>=upLaySAPnum_)
00098                 return (0);
00099         else 
00100                 return (upLayerSAP_[i]);
00101 }
00102 
00103 
00104 int Module::getDownLaySAPnum()
00105 {
00106         return(downLaySAPnum_);
00107 }
00108 
00109 SAP* Module::getDownLaySAP(int i)
00110 {
00111         if (i<0 || i>=downLaySAPnum_)
00112                 return (0);
00113         else 
00114                 return (downLayerSAP_[i]);
00115 }
00116 
00117 
00118 // install a new SAP to an above module
00119 void Module::addUpSAP(SAP* sap)
00120 {
00121         SAP** temp = new SAP*[++upLaySAPnum_];
00122         for (int i = 0; i<(upLaySAPnum_-1); i++)
00123                 temp[i] = upLayerSAP_[i];
00124         temp[upLaySAPnum_ - 1] = sap;
00125         
00126         if (upLayerSAP_)
00127                 delete [] upLayerSAP_;
00128         
00129         if(debug_>1)
00130         {
00131                 printf("Module::addUpSAP(%p) -- upLaySAPnum_=%i\n", sap, upLaySAPnum_);
00132                 if(debug_ > 1)
00133                 {
00134                         for(int i = 0; i<upLaySAPnum_; i++)
00135                                 printf("\ttemp[%i]=%p\n",i,temp[i]);
00136                 }
00137         }
00138         upLayerSAP_ = temp;
00139 }
00140 
00141 // install a new SAP to a bottom module
00142 void Module::addDownSAP(SAP* sap)
00143 {
00144         SAP** temp = new SAP*[++downLaySAPnum_];
00145         for (int i = 0; i<(downLaySAPnum_-1); i++)
00146                 temp[i] = downLayerSAP_[i];
00147         temp[downLaySAPnum_ - 1] = sap;
00148         if (downLayerSAP_)
00149                 delete [] downLayerSAP_;
00150         downLayerSAP_ = temp;
00151         if(debug_ >= 1)
00152         {
00153                 printf("(%p) Module %i downLayerSAP_[%i] = %p \n", this, getId(), (downLaySAPnum_ - 1), sap);
00154         }
00155 }
00156 
00157 
00158 void Module::swapUpLaySAP(int i, int j)
00159 {
00160         
00161         if ( (i<0) || (i>=upLaySAPnum_) || (j<0) || (j>=upLaySAPnum_) || (i==j) )
00162         {
00163                 fprintf(stderr, "Module::swapUpLaySAP, try to swap uncoherent SAPs (%d <-> %d)",i,j);
00164                 exit(1);
00165         }
00166         SAP* temp;
00167         temp = upLayerSAP_[i];
00168         upLayerSAP_[i] = upLayerSAP_[j];
00169         upLayerSAP_[j] = temp;
00170         return;
00171 }
00172 
00173 void Module::swapDownLaySAP(int i, int j)
00174 {
00175         if ( (i<0) || (i>=downLaySAPnum_) || (j<0) || (j>=downLaySAPnum_) || (i==j) )
00176         {
00177                 fprintf(stderr, "Module::swapDownLaySAP, try to swap uncoherent SAPs (%d <-> %d)",i,j);
00178                 exit(1);
00179         }
00180         SAP* temp;
00181         temp = downLayerSAP_[i];
00182         downLayerSAP_[i] = downLayerSAP_[j];
00183         downLayerSAP_[j] = temp;
00184         return;
00185 
00186 }
00187 
00188 
00189 
00190 void Module::sendUp(Packet* p,  double delay)
00191 {
00192         // by default a module send a packet to all the modules of the above layer
00193         if (upLaySAPnum_<=0)
00194         {
00195                 fprintf(stderr,"Error Module.sendUp(): no SAP installed\n");
00196                 exit(1);
00197         }
00198         if(upLaySAPnum_ == 1)
00199         {
00200                 if(debug_ >= 1)
00201                 {
00202                         printf("\t %f upLayerSAP_[0]=%p (this=%p id=%i)\n", Scheduler::instance().clock(), upLayerSAP_[0], this, getId());
00203                         fflush(stdout);
00204                 }
00205                 upLayerSAP_[0]->sendUp(p, delay);
00206         }
00207         else
00208         {
00209                 for(int i=0; i<upLaySAPnum_; i++)
00210                 {
00211                         upLayerSAP_[i]->sendUp(copy(p), delay);
00212                 }
00213                 Packet::free(p);
00214         }
00215 }
00216 
00217 
00218  void Module::sendDown(Packet* p,  double delay)
00219  {
00220         // by default a module send a packet to all the modules of the bottom layer
00221         if (downLaySAPnum_<=0)
00222         {
00223                 fprintf(stderr,"Error Module.sendDown(): no SAP installed\n");
00224                 exit(1);
00225         }
00226         if(debug_ > 10)
00227                 printf("Module::sendDown(%p,%f) ---- downLaySAPnum_=%i\n", p, delay, downLaySAPnum_);
00228         if(downLaySAPnum_ == 1)
00229         {
00230                 if(debug_ >= 1)
00231                 {
00232                         printf("\t %f downLayerSAP_[0]=%p (this=%p id=%i)\n", Scheduler::instance().clock(), downLayerSAP_[0], this, getId());
00233                         fflush(stdout);
00234                 }
00235                 downLayerSAP_[0]->sendDown(p, delay);
00236         }
00237         else
00238         {
00239                 for(int i=0; i<downLaySAPnum_; i++)
00240                 {
00241                         if(debug_ >= 1)
00242                         {
00243                                 printf("\tdownLayerSAP_[%i]=%p\n", i, downLayerSAP_[i]);
00244                                 fflush(stdout);
00245                         }
00246                         Packet *pkt = copy(p);
00247                         downLayerSAP_[i]->sendDown(pkt, delay);
00248                 }
00249                 Packet::free(p);
00250         }
00251 }
00252 
00253 // send a packet to the above specified module
00254 void Module::sendUp(int moduleId, Packet* p,  double delay)
00255  {
00256         bool find = FALSE;
00257         SAP* sap = 0;
00258         for(int i = 0; i<upLaySAPnum_; i++)
00259         {
00260                 sap = getUpLaySAP(i);
00261                 if(debug_ > 1)
00262                         printf("Module::sendUp - trovato module con id=%i\n", sap->getModuleDownId());
00263                 if (sap->getModuleUpId()==moduleId)
00264                 {
00265                         find = TRUE;
00266                         break;
00267                 }
00268         }
00269         if (find)
00270         {
00271                 sap->sendUp(p, delay);
00272                 return;
00273         } else {
00274                 fprintf(stderr,"Error Module.sendUp(): invalid moduleId %d\n",moduleId);
00275                 char tag[20];
00276                 getTag(tag,20);
00277                 fprintf(stderr,"This module: tag \"%s\", id %d, %d SAPs above and %d below\n",
00278                         tag,getId(),getUpLaySAPnum(),getDownLaySAPnum());
00279                 exit(1);
00280         }
00281  }
00282 
00283 // send a packet to the bottom specified module
00284  void Module::sendDown(int moduleId, Packet* p,  double delay)
00285  {
00286         
00287         bool find = FALSE;
00288         SAP* sap = 0;
00289         for(int i = 0; i<downLaySAPnum_; i++)
00290         {
00291                 sap = getDownLaySAP(i);
00292                 if (sap->getModuleDownId()==moduleId)
00293                 {
00294                         find = TRUE;
00295                         break;
00296                 }
00297         }
00298         if (find)
00299         {
00300                 sap->sendDown(p, delay);
00301                 return;
00302         } else {
00303                 fprintf(stderr,"Error Module.sendDown(): invalid moduleId specified\n");
00304                 exit(1);
00305         }
00306 }
00307 
00308 void Module::sendUp(ClMessage* m,  double delay)
00309 {
00310   PRINT_WARNING_DEPRECATED_FUNCTION;
00311   sendAsyncClMsgUp(m, delay);
00312 }
00313 
00314 void Module::sendDown(ClMessage* m,  double delay)
00315 {
00316   PRINT_WARNING_DEPRECATED_FUNCTION;
00317   sendAsyncClMsgDown(m, delay);
00318 }
00319 
00320 
00321 void Module::sendDown(int moduleId, ClMessage* m,  double delay)
00322 {
00323   PRINT_WARNING_DEPRECATED_FUNCTION;
00324   m->setDest(moduleId);
00325   sendAsyncClMsgDown(m, delay);
00326 }
00327 
00328 
00329 void Module::sendUp(int moduleId, ClMessage* m,  double delay)
00330 {
00331   PRINT_WARNING_DEPRECATED_FUNCTION;
00332   m->setDest(moduleId);
00333   sendAsyncClMsgUp(m, delay);
00334 }
00335 
00336 
00337 void Module::sendSynchronousUp(ClMessage* m)
00338 {
00339   PRINT_WARNING_DEPRECATED_FUNCTION;
00340   sendSyncClMsgUp(m);
00341 }
00342 
00343 
00344 void Module::sendSynchronousDown(ClMessage* m)
00345 {
00346   PRINT_WARNING_DEPRECATED_FUNCTION;
00347   sendSyncClMsgDown(m);
00348 }
00349 
00350 
00351 void Module::sendSynchronousDown(int moduleId, ClMessage* m)
00352 {
00353   PRINT_WARNING_DEPRECATED_FUNCTION;
00354   m->setDest(moduleId);
00355   sendSyncClMsgDown(m);
00356 }
00357 
00358 void Module::sendSynchronousUp(int moduleId, ClMessage* m)
00359 {
00360   PRINT_WARNING_DEPRECATED_FUNCTION;
00361   m->setDest(moduleId);
00362   sendSyncClMsgUp(m);
00363 }
00364 
00365 
00366 void Module::sendAsyncClMsgUp(ClMessage* m,  double delay)
00367 {
00368   assert(m);
00369   m->setSource(getId()); // this makes src IDs more spoofing-proof
00370   int dest = m->getDest();
00371   bool is_broadcast = ( m->getDestType() == BROADCAST);
00372 
00373   
00374   if (is_broadcast && (dest != CLBROADCASTADDR) && (debug_ >= 0))
00375     cerr << __PRETTY_FUNCTION__ << " broadcast message with dest_ != CLBROADCASTADDR (dest_=" << dest << ")" << endl;
00376 
00377   if ((upLaySAPnum_<=0) && (debug_ >= 0))
00378     cerr << __PRETTY_FUNCTION__ << " upLaySAPnum_ <= 0 " << endl;
00379 
00380   bool found = false;
00381 
00382   for(int i=0; i<upLaySAPnum_; i++)
00383     {
00384       SAP* sap = getUpLaySAP(i);
00385 
00386       if (is_broadcast || (dest == sap->getModuleUpId()))
00387         {      
00388           // Note that we cannot send m because we need it for further copies
00389           // If we send m then it might have been deleted when we try to make a copy of it
00390           sap->sendUp(m->copy(), delay); 
00391           found = true;
00392         }
00393     }
00394 
00395   delete m;
00396 
00397   if (!found)
00398     {
00399 
00400       if  (debug_ >= 0)
00401         cerr << __PRETTY_FUNCTION__ << " no destination found" << endl;
00402     }      
00403     
00404 
00405 }
00406 
00407 void Module::sendAsyncClMsgDown(ClMessage* m,  double delay)
00408 {
00409 
00410   assert(m);
00411   m->setSource(getId()); // this makes src IDs more spoofing-proof
00412   int dest = m->getDest();
00413   bool is_broadcast = ( m->getDestType() == BROADCAST);
00414   
00415   if (is_broadcast && (dest != CLBROADCASTADDR) && (debug_ >= 0))
00416     cerr << __PRETTY_FUNCTION__ << " broadcast message with dest_ != CLBROADCASTADDR (dest_=" << dest << ")" << endl;
00417 
00418   if ((downLaySAPnum_<=0) && (debug_ >= 0))
00419     cerr << __PRETTY_FUNCTION__ << " downLaySAPnum_ <= 0 " << endl;
00420 
00421   bool found = false;
00422 
00423   for(int i=0; i<downLaySAPnum_; i++)
00424     {
00425       SAP* sap = getDownLaySAP(i);
00426 
00427       if (is_broadcast || (dest == sap->getModuleDownId()))
00428         {
00429           // Note that we cannot send m because we need it for further copies
00430           // If we send m then it might have been deleted when we try to make a copy of it
00431           sap->sendDown(m->copy(), delay);
00432           found = true;
00433         }
00434     }
00435 
00436   delete m;
00437 
00438   if (!found)
00439     {
00440       if  (debug_ >= 0)
00441         cerr << __PRETTY_FUNCTION__ << " no destination found" << endl;
00442     }      
00443     
00444 }
00445 
00446 void Module::sendSyncClMsgUp(ClMessage* m)
00447 {
00448   assert(m);
00449   m->setSource(getId()); // this makes src IDs more spoofing-proof
00450   int dest = m->getDest();
00451   bool is_broadcast = ( m->getDestType() == BROADCAST);
00452   
00453   if (is_broadcast && (dest != CLBROADCASTADDR) && (debug_ >= 0))
00454     cerr << __PRETTY_FUNCTION__ << " broadcast message with dest_ != CLBROADCASTADDR (dest_=" << dest << ")" << endl;
00455 
00456   if ((upLaySAPnum_<=0) && (debug_ >= 0))
00457     cerr << __PRETTY_FUNCTION__ << " upLaySAPnum_ <= 0 " << endl;
00458 
00459   bool found = false;
00460 
00461   for(int i=0; i<upLaySAPnum_; i++)
00462     {
00463       SAP* sap = getUpLaySAP(i);
00464 
00465       if (is_broadcast || (dest == sap->getModuleUpId()))
00466         {
00467           sap->sendSynchronousUp(m); // first message
00468           found = true;
00469         }
00470     }
00471 
00472   if ((!found) && (debug_ >= 0))
00473     cerr << __PRETTY_FUNCTION__ << " no destination found" << endl;
00474 }      
00475 
00476 void Module::sendSyncClMsgDown(ClMessage* m)
00477 {
00478   assert(m);
00479   m->setSource(getId()); // this makes src IDs more spoofing-proof
00480   int dest = m->getDest();
00481   bool is_broadcast = ( m->getDestType() == BROADCAST);
00482   
00483   if (is_broadcast && (dest != CLBROADCASTADDR) && (debug_ >= 0))
00484     cerr << __PRETTY_FUNCTION__ << " broadcast message with dest_ != CLBROADCASTADDR (dest_=" << dest << ")" << endl;
00485 
00486   if ((downLaySAPnum_<=0) && (debug_ >= 0))
00487     cerr << __PRETTY_FUNCTION__ << " downLaySAPnum_ <= 0 " << endl;
00488 
00489   bool found = false;
00490 
00491   for(int i=0; i<downLaySAPnum_; i++)
00492     {
00493       SAP* sap = getDownLaySAP(i);
00494 
00495       if (is_broadcast || (dest == sap->getModuleDownId()))
00496         {
00497           sap->sendSynchronousDown(m); // first message
00498           found = true;
00499         }
00500     }
00501 
00502   if ((!found) && (debug_ >= 0))
00503     cerr << __PRETTY_FUNCTION__ << " no destination found" << endl;
00504 }      
00505     
00506 
00507 
00508 
00509 void Module::drop(Packet* p, int depth, const char* reason)
00510 {
00511         if (binPtr_==0)
00512         {
00513                 fprintf(stderr, "Error Module.drop(packet): no bin installed\n");
00514                 exit(1);
00515         }
00516         if(debug_ > 1)
00517                 printf("Module::drop(%p,%i,%s)\n", p, depth, reason);
00518         char *temp = new char[MAX_TAG_LENGTH + strlen(reason)+2];
00519         strcpy(temp, tag_);
00520         strcat(temp, " ");
00521         strcat(temp, reason);
00522         if(debug_ > 1)
00523                 printf("\ttemp=%s\n", temp);
00524         binPtr_->drop(p, depth, temp);
00525         delete [] temp;
00526 }
00527 
00528 void Module::recv(Packet *p, Handler* callback)
00529 {
00530         recv(p);
00531 }
00532 
00533 void Module::recv(Packet *p, int idSrc)
00534 {
00535         recv(p);
00536 }
00537 
00538 Packet *Module::copy(Packet *p)
00539 {
00540         Packet *pkt = p->copy();
00541         pkt->txinfo_.RxPr = p->txinfo_.RxPr;    
00542         pkt->txinfo_.CPThresh = p->txinfo_.CPThresh;
00543 
00544         return pkt;
00545 }

Generated on Wed Nov 26 15:47:28 2008 for NS-MIRACLE library by  doxygen 1.5.2