User Manual, Developers Guide and API Documentation

BCHUnit.cpp

Go to the documentation of this file.
00001 /*******************************************************************************
00002  * This file is part of openWNS (open Wireless Network Simulator)
00003  * _____________________________________________________________________________
00004  *
00005  * Copyright (C) 2004-2007
00006  * Chair of Communication Networks (ComNets)
00007  * Kopernikusstr. 5, D-52074 Aachen, Germany
00008  * phone: ++49-241-80-27910,
00009  * fax: ++49-241-80-22242
00010  * email: info@openwns.org
00011  * www: http://www.openwns.org
00012  * _____________________________________________________________________________
00013  *
00014  * openWNS is free software; you can redistribute it and/or modify it under the
00015  * terms of the GNU Lesser General Public License version 2 as published by the
00016  * Free Software Foundation;
00017  *
00018  * openWNS is distributed in the hope that it will be useful, but WITHOUT ANY
00019  * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
00020  * A PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more
00021  * details.
00022  *
00023  * You should have received a copy of the GNU Lesser General Public License
00024  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
00025  *
00026  ******************************************************************************/
00027 
00028 #include <LTE/controlplane/bch/BCHUnit.hpp>
00029 #include <LTE/timing/ResourceScheduler.hpp>
00030 #include <LTE/controlplane/associationHandler/AssociationHandler.hpp>
00031 #include <LTE/controlplane/flowmanagement/FlowManager.hpp>
00032 #include <LTE/rlc/RLCCommand.hpp>
00033 
00034 #include <DLL/Layer2.hpp>
00035 #include <DLL/services/control/Association.hpp>
00036 
00037 #include <WNS/ldk/fun/FUN.hpp>
00038 #include <WNS/ldk/helper/FakePDU.hpp>
00039 
00040 using namespace lte;
00041 using namespace lte::controlplane::bch;
00042 using namespace wns;
00043 using namespace wns::ldk;
00044 using namespace wns::ldk::fun;
00045 
00046 STATIC_FACTORY_REGISTER_WITH_CREATOR(LTEBCHUnitRAP, FunctionalUnit, "lte.controlplane.BCHUnit.RAP", FUNConfigCreator);
00047 STATIC_FACTORY_REGISTER_WITH_CREATOR(LTEBCHUnitUT, FunctionalUnit, "lte.controlplane.BCHUnit.UT", FUNConfigCreator);
00048 STATIC_FACTORY_REGISTER_WITH_CREATOR(NoBCH, FunctionalUnit, "lte.controlplane.BCHUnit.No", FUNConfigCreator);
00049 
00050 
00051 LTEBCHUnit::LTEBCHUnit(wns::ldk::fun::FUN* fun, const pyconfig::View& config) :
00052   CommandTypeSpecifier<LTEBCHCommand>(fun),
00053   HasReceptor<>(),
00054   HasConnector<>(),
00055   HasDeliverer<>(),
00056   lte::helper::HasModeName(config),
00057 
00058   logger(config.get("logger")),
00059   layer2(NULL),
00060   commandSize(config.get<int>("commandSize"))
00061 {
00062     friends.scheduler = NULL;
00063     friends.macg = NULL;
00064 
00065     rlcReader = NULL;
00066 }
00067 
00068 
00069 LTEBCHUnitRAP::LTEBCHUnitRAP(wns::ldk::fun::FUN* fun, const pyconfig::View& config) :
00070   LTEBCHUnit(fun, config),
00071   Cloneable<LTEBCHUnitRAP>(),
00072   txPower(config.get<wns::Power>("txPower")),
00073   accepting(false),
00074   compound(CompoundPtr()),
00075   rlcName(config.get<std::string>("rlcName")),
00076   macgName(config.get<std::string>("macgName")),
00077   flowManagerName(config.get<std::string>("flowManagerName"))
00078 {
00079 }
00080 
00081 LTEBCHUnitUT::LTEBCHUnitUT(wns::ldk::fun::FUN* fun, const pyconfig::View& _config) :
00082   LTEBCHUnit(fun, _config),
00083   Cloneable<LTEBCHUnitUT>(),
00084 
00085   bchService(NULL),
00086   associationService(NULL),
00087   config(_config),
00088   sinrProbe(NULL),
00089   rxpProbe(NULL),
00090   interfProbe(NULL),
00091   schedulerName(config.get<std::string>("schedulerName"))
00092 {
00093   MESSAGE_SINGLE(NORMAL, logger, "LTEBCHUnit for mode " << modeBase << " started.");
00094 }
00095 
00096 LTEBCHUnit::~LTEBCHUnit()
00097 {
00098   layer2 = NULL;
00099 }
00100 
00101 LTEBCHUnitRAP::~LTEBCHUnitRAP()
00102 {
00103   compound = CompoundPtr();
00104 }
00105 
00106 LTEBCHUnitUT::~LTEBCHUnitUT()
00107 {
00108   associationService = NULL;
00109   bchService = NULL;
00110 
00111   delete sinrProbe; sinrProbe = NULL;
00112   delete rxpProbe; rxpProbe = NULL;
00113   delete interfProbe; interfProbe = NULL;
00114 }
00115 
00116 void
00117 LTEBCHUnit::onFUNCreated()
00118 {
00119     layer2 = getFUN()->getLayer<dll::ILayer2*>();
00120 }
00121 
00122 void
00123 LTEBCHUnitRAP::onFUNCreated()
00124 {
00125     LTEBCHUnit::onFUNCreated();
00126     rlcReader = getFUN()->getCommandReader(rlcName);
00127     friends.macg = getFUN()->findFriend<lte::macg::MACg*>(macgName);
00128 }
00129 
00130 void
00131 LTEBCHUnitUT::onFUNCreated()
00132 {
00133   LTEBCHUnit::onFUNCreated();
00134 
00135   bchService = layer2->getControlService<lte::controlplane::bch::BCHService>("BCHSERVICE"+separator+mode);
00136   associationService = layer2->getControlService<dll::services::control::Association>("ASSOCIATION"+modeBase);
00137 
00138   wns::node::Interface* node = layer2->getNode();
00139   wns::probe::bus::ContextProviderCollection localIDs(&node->getContextProviderCollection());
00140 
00141   friends.scheduler = getFUN()->findFriend<lte::timing::ResourceScheduler*>(schedulerName);
00142 
00143   // read the localIDs from the config
00144   for (int ii = 0; ii<config.len("localIDs.keys()"); ++ii)
00145     {
00146       std::string key = config.get<std::string>("localIDs.keys()",ii);
00147       uint32_t value  = config.get<uint32_t>("localIDs.values()",ii);
00148       localIDs.addProvider(wns::probe::bus::contextprovider::Constant(key, value));
00149       MESSAGE_SINGLE(VERBOSE, logger, "Using Local IDName '"<<key<<"' with value: "<<value);
00150     }
00151   sinrProbe   = new wns::probe::bus::ContextCollector(localIDs, "lte.BCH_SINR");
00152   rxpProbe    = new wns::probe::bus::ContextCollector(localIDs, "lte.BCH_RxPower");
00153   interfProbe = new wns::probe::bus::ContextCollector(localIDs, "lte.BCH_Interference");
00154 }
00155 
00156 
00157 bool
00158 LTEBCHUnitRAP::doIsAccepting(const CompoundPtr& /* compound */) const
00159 {
00160   return accepting;
00161 } // isAccepting
00162 
00163 bool
00164 LTEBCHUnitUT::doIsAccepting(const CompoundPtr& /* compound */) const
00165 {
00166   return false;
00167 }
00168 
00169 void
00170 LTEBCHUnitRAP::doSendData(const CompoundPtr& _compound)
00171 {
00172   LTEBCHCommand* myCommand;
00173   if (compound == CompoundPtr()) // if first Association ACK
00174     {
00175       compound = CompoundPtr(new Compound(getFUN()->createCommandPool()));
00176       myCommand = activateCommand(compound->getCommandPool());
00177       myCommand->magic.source = layer2->getDLLAddress();
00178       myCommand->peer.acknowledgement = true;
00179       myCommand->peer.ackedUTs.push_back(_compound);
00180     }
00181   else // use the existing BCH compound and just append the Association ACK into it
00182     {
00183       myCommand = getCommand(compound->getCommandPool());
00184       myCommand->peer.ackedUTs.push_back(_compound);
00185     }
00186 } // doSendData
00187 
00188 void
00189 LTEBCHUnitUT::doSendData(const CompoundPtr&)
00190 {}
00191 
00192 void
00193 LTEBCHUnitRAP::doOnData(const CompoundPtr&)
00194 {
00195 }
00196 
00197 void
00198 LTEBCHUnitUT::doOnData(const CompoundPtr& compound)
00199 {
00201     lte::timing::SchedulerCommand* schedulerCommand = friends.scheduler->getCommand(compound->getCommandPool());
00202   LTEBCHCommand* myCommand = getCommand(compound->getCommandPool());
00203 
00204   wns::service::dll::UnicastAddress comingFrom = myCommand->magic.source;
00206   assure(bchService, "LTEBCHUnit unexpectedly received a BCH compound.");
00207   bchService->storeMeasurement(comingFrom, schedulerCommand->local.phyMeasurementPtr, schedulerCommand->local.subBand);
00208 
00209   { // Probe measurement Values
00210     assure(associationService, "Trying to probe BCH Measurement in a RAP.");
00211 
00212     if (associationService->hasAssociation())
00213       if (associationService->getAssociation() == comingFrom)
00214     {
00215         wns::service::phy::power::PowerMeasurementPtr phyMeasurementPtr = schedulerCommand->local.phyMeasurementPtr;
00216       sinrProbe->put(compound, phyMeasurementPtr->getSINR().get_dB());
00217       rxpProbe->put(compound, phyMeasurementPtr->getRxPower().get_dBm());
00218       interfProbe->put(compound, phyMeasurementPtr->getInterferencePower().get_dBm());
00219     }
00220   }
00221 
00222   if (myCommand->peer.acknowledgement)
00223     {
00224       assure(!myCommand->peer.ackedUTs.empty(), "BCH compound does not contain Association ACKs, but should do so!");
00225       // send the Association ACKs tp the AssociationHandler FU. The filtering by the MAC address will be done there
00226       for(std::list<wns::ldk::CompoundPtr>::const_iterator iter = myCommand->peer.ackedUTs.begin(); iter != myCommand->peer.ackedUTs.end(); ++iter)
00227     {
00228       getDeliverer()->getAcceptor(compound)->onData(*iter);
00229     }
00230       myCommand->peer.ackedUTs.clear();
00231     }
00232   // else the compound is dropped here
00233 } // doOnData
00234 
00235 void
00236 LTEBCHUnitRAP::doWakeup()
00237 {
00238   getReceptor()->wakeup();
00239 } // wakeup
00240 
00241 void
00242 LTEBCHUnitUT::doWakeup()
00243 {
00244 }
00245 
00246 void
00247 LTEBCHUnit::calculateSizes(const CommandPool* commandPool, Bit& _commandPoolSize, Bit& _dataSize) const
00248 {
00249   getFUN()->getProxy()->calculateSizes(commandPool, _commandPoolSize, _dataSize, this);
00250   _commandPoolSize += this->commandSize;
00251 }
00252 
00253 void LTEBCHUnitRAP::sendBCH(simTimeType duration)
00254 {
00255   assure(rlcReader, "You may not use the  'sendBCH' Event without an RLC in your FUN");
00256 
00257   MESSAGE_SINGLE(NORMAL, logger, "sendBCH(): Creating BCH");
00258 
00259   accepting = true;
00260   // if there are pending Association ACKs in the BCH buffer, they will be stored in peer.ackedUTs now
00261   this->wakeup();
00262   accepting = false;
00263 
00264   if (compound == CompoundPtr()) //no compound from associationHandler FU
00265     {
00266       compound = CompoundPtr(new Compound(getFUN()->createCommandPool(),
00267                                           wns::ldk::helper::FakePDUPtr(new wns::ldk::helper::FakePDU(1))));
00268       LTEBCHCommand* myCommand = activateCommand(compound->getCommandPool());
00269       myCommand->magic.source = layer2->getDLLAddress();
00270       myCommand->peer.acknowledgement = false;
00271       myCommand->peer.ackedUTs.clear();
00272     }
00273 
00274     // set RLC Command
00275     lte::rlc::RLCCommand* rlcCommand = dynamic_cast<lte::rlc::RLCCommand*>(rlcReader->activateCommand(compound->getCommandPool()));
00276 
00277     // Downlink
00278     rlcCommand->local.direction = 2;
00279     rlcCommand->peer.source = layer2->getDLLAddress();
00280     rlcCommand->peer.destination = wns::service::dll::UnicastAddress();
00281     rlcCommand->peer.qosClass = lte::helper::QoSClasses::PBCH();
00282     rlcCommand->peer.flowID = layer2->getControlService<lte::controlplane::flowmanagement::FlowManager>(flowManagerName)->getBCHFlowID();
00283 
00284     // set MACg Command
00285     lte::macg::MACgCommand* macgCommand =
00286         dynamic_cast<lte::macg::MACgCommand*>(getFUN()->getProxy()->activateCommand(compound->getCommandPool(), friends.macg ));
00287     macgCommand->peer.source = layer2->getDLLAddress();
00288     macgCommand->peer.dest = wns::service::dll::UnicastAddress();
00289 
00290   if (getConnector()->hasAcceptor(compound)){
00291     MESSAGE_SINGLE(NORMAL, logger, "sendBCH(): BCH created");
00293     //MESSAGE_SINGLE(NORMAL, logger, "sendBCH(): BCH created (PhyMode " << modulation << "-" << coding <<")");
00294     getConnector()->getAcceptor(compound)->sendData(compound);
00295   }
00296   else
00297       assure(false, "Lower FU is not accepting scheduled PDU but is supposed to do so");
00298 
00299   compound = CompoundPtr();
00300 }

Generated on Mon May 21 03:32:02 2012 for openWNS by  doxygen 1.5.5