link_channel.cc

00001 /*
00002  * Copyright (c) 2007 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 #include <iostream>
00031 
00032 #include"link_channel.h"
00033 
00034 
00035 
00036 class LinkChannelModuleClass : public TclClass {
00037 public:
00038         LinkChannelModuleClass() : TclClass("Module/Link") {}
00039         TclObject* create(int, const char*const*) {
00040           return (new LinkChannelModule());
00041         }
00042 } class_module_channel_link;
00043 
00044 
00045 LinkChannelModule::LinkChannelModule() : linkhead_(0), srcsap(0), dstsap(0) 
00046 {
00047 
00048 }
00049 
00050 LinkChannelModule::~LinkChannelModule()  
00051 {
00052 
00053 }
00054 
00055 
00056 
00057 int LinkChannelModule::command(int argc, const char*const* argv)
00058 {
00059 
00060   Tcl& tcl = Tcl::instance();
00061   
00062     if(argc == 3)
00063     {
00064 
00065       if (strcasecmp(argv[1],"addsap")==0)
00066         {
00067           // intercept this command so we can set srcsap and dstsap
00068           // quite a wild hack, it depends on the order in which ChSAPs are added
00069           ChSAP *chsap = dynamic_cast<ChSAP*>(TclObject::lookup(argv[2]));
00070 
00071           if (srcsap == NULL) 
00072             {
00073               srcsap = chsap;
00074             }
00075           else
00076             {
00077               if (debug_)
00078                 {
00079                   if (dstsap)
00080                     {
00081                       cerr << "dstsap:" << dstsap 
00082                            << "  addsap:" << chsap << endl;
00083                     }
00084                 }
00085               assert (dstsap == NULL); // this will fail if you try to attach more than two ChSAPs 
00086               dstsap = chsap;      
00087             }
00088           // we still need the parent method
00089           return ChannelModule::command(argc,argv);
00090 
00091         }
00092       else if(strcasecmp(argv[1], "setLinkHead")==0)
00093         {
00094           linkhead_ = (NsObject *)TclObject::lookup(argv[2]);
00095             
00096           if(!linkhead_) 
00097             return TCL_ERROR;
00098 
00099           // link head is not the tail!!! We can't do this!
00100           //tcl.evalf("%s target %s",linkhead_->name(), name());                  
00101           return TCL_OK;                  
00102         }
00103 
00104     }
00105       
00106   /* If command is unknown, fallback to parent command intepreter */      
00107   return  ChannelModule::command(argc,argv);
00108   
00109 
00110 }
00111 
00112 
00113 
00114 
00115 void LinkChannelModule::recv(Packet* p, ChSAP* cs)
00116 {
00117   assert(linkhead_ != NULL);
00118 
00119   if (cs != srcsap)
00120     {
00121       if (debug_) 
00122         cerr <<  this <<" packet received from the wrong ChSAP - Module/Link is unidirectional!" << endl;      
00123 
00124       // drop(p,5,LINKCH_DROP_REASON_WRONG_DIRECTION);
00125       Packet::free(p);
00126       return;
00127     }
00128 
00129   if (debug_) 
00130     cerr << this << " received packet from ChSAP" << cs << " (srcsap=" << srcsap << "), sending to  " << linkhead_ << endl;
00131 
00132   linkhead_->recv(p, (Handler *) 0);
00133   
00134 }
00135 
00136 
00137 void LinkChannelModule::recv(Packet* p, Handler* h)
00138 {
00139 
00140   hdr_cmn* ch = hdr_cmn::access(p);
00141 
00142   if (ch->error())
00143     {
00144       drop(p,1,LINKCH_DROP_REASON_ERROR);
00145       return;
00146     }
00147 
00148   
00149   if (debug_) 
00150     cerr << this <<" sending packet from " << h << " (srcsap=" << srcsap << ") to dstsap " <<  dstsap << endl;
00151   
00152   dstsap->sendUp(p,0);
00153 }

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