PhyLayerUWBIR.cc

00001 #include "PhyLayerUWBIR.h"
00002 #include <cassert>
00003 #include "MacToUWBIRPhyControlInfo.h"
00004 #include "AirFrameUWBIR_m.h"
00005 
00006 Define_Module(PhyLayerUWBIR);
00007 
00008 //cDynamicExpression::Value (PhyLayerUWBIR::*ghassemzadehNLOSFPtr) (cComponent *context, cDynamicExpression::Value argv[], int argc) = &ghassemzadehNLOSFunc;
00009 PhyLayerUWBIR::fptr ghassemzadehNLOSFPtr = &PhyLayerUWBIR::ghassemzadehNLOSFunc;
00010 Define_NED_Function(ghassemzadehNLOSFPtr, "xml ghassemzadehNLOS()");
00011 
00012 void PhyLayerUWBIR::initialize(int stage) {
00013   BasePhyLayer::initialize(stage);
00014   if (stage == 0) {
00015 
00016 
00017     numActivities = 6;
00018 
00019     // Power consumption (from PhyLayerBattery)
00020     /* parameters belong to the NIC, not just phy layer
00021      *
00022      * if/when variable transmit power is supported, txCurrent
00023      * should be specified as an xml table of available transmit
00024      * power levels and corresponding txCurrent */
00025     sleepCurrent = rxCurrent = decodingCurrentDelta = txCurrent = 0;
00026     setupRxCurrent = setupTxCurrent = rxTxCurrent = txRxCurrent = 0;
00027     sleepCurrent = getParentModule()->par( "sleepCurrent" );
00028     rxCurrent = getParentModule()->par( "rxCurrent" );
00029 //    decodingCurrentDelta = getParentModule()->par( "decodingCurrentDelta" );
00030     txCurrent = getParentModule()->par( "txCurrent" );
00031     setupRxCurrent = getParentModule()->par( "setupRxCurrent" );
00032     setupTxCurrent = getParentModule()->par( "setupTxCurrent" );
00033     rxTxCurrent = getParentModule()->par( "rxTxCurrent" );
00034     txRxCurrent = getParentModule()->par( "txRxCurrent" );
00035     syncCurrent = getParentModule()->par( "syncCurrent" ); // assume instantaneous transitions between rx and sync
00036   } else if (stage == 1) {
00037     registerWithBattery("physical layer", numActivities);
00038     setRadioCurrent(uwbradio->getCurrentState());
00039   }
00040 
00041 }
00042 
00043 
00044 Radio* PhyLayerUWBIR::initializeRadio() {
00045   int initialRadioState = par("initialRadioState"); //readPar("initalRadioState", (int) RadioUWBIR::SYNC);
00046   double radioMinAtt = readPar("radioMinAtt", 1.0);
00047   double radioMaxAtt = readPar("radioMaxAtt", 0.0);
00048 
00049   uwbradio = RadioUWBIR::createNewUWBIRRadio(initialRadioState, recordStats, radioMinAtt, radioMaxAtt);
00050 
00051   //  - switch times to TX
00052   simtime_t rxToTX = readPar("timeRXToTX", 0.0);
00053   simtime_t sleepToTX = readPar("timeSleepToTX", 0.0);
00054 
00055   // Radio timers
00056   // From Sleep mode
00057   uwbradio->setSwitchTime(RadioUWBIR::SLEEP, RadioUWBIR::RX, par("timeSleepToRX"));
00058   uwbradio->setSwitchTime(RadioUWBIR::SLEEP, RadioUWBIR::TX, par("timeSleepToTX"));
00059   uwbradio->setSwitchTime(RadioUWBIR::SLEEP, RadioUWBIR::SLEEP, 0);
00060 
00061   // From TX mode
00062   uwbradio->setSwitchTime(RadioUWBIR::TX, RadioUWBIR::SYNC, par("timeTXToRX"));
00063   uwbradio->setSwitchTime(RadioUWBIR::TX, RadioUWBIR::RX, par("timeTXToRX"));
00064 
00065   // From RX mode
00066   uwbradio->setSwitchTime(RadioUWBIR::RX, RadioUWBIR::TX, par("timeRXToTX"));
00067   uwbradio->setSwitchTime(RadioUWBIR::RX, RadioUWBIR::SYNC, 0.000000001);
00068   uwbradio->setSwitchTime(RadioUWBIR::SYNC, RadioUWBIR::TX, par("timeRXToTX"));
00069 
00070   // From SYNC mode
00071   uwbradio->setSwitchTime(RadioUWBIR::SYNC, RadioUWBIR::RX, 0.000000001);
00072 
00073   return uwbradio;
00074 }
00075 
00076 AnalogueModel* PhyLayerUWBIR::getAnalogueModelFromName(std::string name,
00077     ParameterMap& params) {
00078   if (name == "UWBIRStochasticPathlossModel")
00079     return createUWBIRStochasticPathlossModel(params);
00080 
00081   if (name == "UWBIRIEEE802154APathlossModel")
00082     return createUWBIRIEEE802154APathlossModel(params);
00083 
00084   if (name == "RadioStateAnalogueModel")
00085     return uwbradio->getAnalogueModel();
00086 
00087   return 0;
00088 }
00089 
00090 /*
00091  *Returns an AnalogueModel object which will be stored in the
00092  * analogueModels list. All AnalogueModel objects are successively applied
00093  * to any signal at the beginning of its reception, and their outputs
00094  * (attenuations objects) are then associated to the incoming signal object.
00095  **/
00096 AnalogueModel* PhyLayerUWBIR::createUWBIRStochasticPathlossModel(
00097     ParameterMap & params) {
00098   //get the pathloss exponent parameter from the config
00099   ParameterMap::iterator it = params.find("PL0");
00100   double PL0 = it->second.doubleValue();
00101   it = params.find("mu_gamma");
00102   if (it == params.end()) {
00103     error(
00104         "Could not find required double parameter <mu_gamma> in the Ghassemzadeh channel xml description file.");
00105   }
00106   double mu_gamma = it->second.doubleValue();
00107   it = params.find("sigma_gamma");
00108   if (it == params.end()) {
00109     error(
00110         "Could not find required double parameter <sigma_gamma> in the Ghassemzadeh channel xml description file.");
00111   }
00112   double sigma_gamma = it->second.doubleValue();
00113   it = params.find("mu_sigma");
00114   if (it == params.end()) {
00115     error(
00116         "Could not find required double parameter <mu_sigma> in the Ghassemzadeh channel xml description file.");
00117   }
00118   double mu_sigma = it->second.doubleValue();
00119   it = params.find("sigma_sigma");
00120   if (it == params.end()) {
00121     error(
00122         "Could not find required double parameter <sigma_sigma> in the Ghassemzadeh channel xml description file.");
00123   }
00124   double sigma_sigma = it->second.doubleValue();
00125 
00126   it = params.find("isEnabled");
00127   if (it == params.end()) {
00128     error(
00129         "Could not find required bool parameter <isEnabled> in the Ghassemzadeh channel xml description file.");
00130   }
00131   bool isEnabled = it->second.boolValue();
00132 
00133   bool shadowing = true;
00134   it = params.find("shadowing");
00135   if (it != params.end()) {
00136     shadowing = it->second.boolValue();
00137   }
00138 
00139   uwbpathloss = new UWBIRStochasticPathlossModel(PL0, mu_gamma, sigma_gamma,
00140       mu_sigma, sigma_sigma, &move, isEnabled, shadowing);
00141 
00142   return uwbpathloss;
00143 
00144 }
00145 
00146 AnalogueModel* PhyLayerUWBIR::createUWBIRIEEE802154APathlossModel(ParameterMap & params) {
00147   int CM;
00148   ParameterMap::iterator it = params.find("CM");
00149   if (it == params.end()) {
00150     error(
00151         "Could not find required integer parameter <CM> (Channel Model) in the IEEE 802.15.4A channel xml description file.");
00152   }
00153   CM = int(it->second.longValue());
00154 
00155   double threshold;
00156   it = params.find("Threshold");
00157   if (it == params.end()) {
00158     error("Could not find required double parameter <Threshold> in the IEEE 802.15.4A channel xml description file.");
00159   }
00160   threshold = it->second.doubleValue();
00161 
00162   bool shadowing = false;
00163   it = params.find("shadowing");
00164   if (it != params.end()) {
00165     shadowing = it->second.boolValue();
00166   }
00167 
00168   ieee802154AChannel = new UWBIRIEEE802154APathlossModel(CM, threshold, &move, shadowing);
00169   return ieee802154AChannel;
00170 }
00171 
00172 Decider* PhyLayerUWBIR::getDeciderFromName(std::string name, ParameterMap& params) {
00173   double syncThreshold;
00174   bool stats;
00175   bool trace;
00176   bool syncAlwaysSucceeds;
00177   ParameterMap::iterator it;
00178 
00179   protocolId = IEEE_802154_UWB;
00180 
00181   it = params.find("syncThreshold");
00182   if (it == params.end()) {
00183     error(
00184         "Could not find required double parameter <syncThreshold> in the decider xml configuration file.");
00185   }
00186   syncThreshold = it->second.doubleValue();
00187 
00188   it = params.find("stats");
00189   if (it == params.end()) {
00190     error(
00191         "Could not find required boolean parameter <stats> in the decider xml configuration file.");
00192   }
00193   stats = it->second.boolValue();
00194 
00195   it = params.find("trace");
00196   if (it == params.end()) {
00197     error(
00198         "Could not find required boolean parameter <trace> in the decider xml configuration file.");
00199   }
00200   trace = it->second.boolValue();
00201 
00202   it = params.find("syncAlwaysSucceeds");
00203   if (it == params.end()) {
00204     error(
00205         "Could not find required boolean parameter <syncAlwaysSucceeds> in the decider xml configuration file.");
00206   }
00207   syncAlwaysSucceeds = it->second.boolValue();
00208 
00209   bool alwaysFailOnDataInterference;
00210   it = params.find("alwaysFailOnDataInterference");
00211   if (it == params.end()) {
00212     alwaysFailOnDataInterference = false;
00213   } else {
00214     alwaysFailOnDataInterference = it->second.boolValue();
00215   }
00216 
00217   if (name == "DeciderUWBIREDSyncOnAddress") {
00218     int addr;
00219     it = params.find("addr");
00220     if (it == params.end()) {
00221       error(
00222           "Could not find required int parameter <addr> in the decider xml configuration file.");
00223     }
00224     addr = it->second.longValue();
00225     uwbdecider = new DeciderUWBIREDSyncOnAddress(this, this, syncThreshold,
00226         syncAlwaysSucceeds, stats, trace, addr, alwaysFailOnDataInterference);
00227   }
00228 
00229   if (name == "DeciderUWBIREDSync") {
00230     double tmin;
00231     it = params.find("syncMinDuration");
00232     if (it == params.end()) {
00233       error(
00234           "Could not find required double parameter <syncMinDuration> in the decider xml configuration file.");
00235     }
00236     tmin = it->second.doubleValue();
00237     uwbdecider = new DeciderUWBIREDSync(this, this, syncThreshold, syncAlwaysSucceeds, stats, trace, tmin, alwaysFailOnDataInterference);
00238   }
00239 
00240   if (name=="DeciderUWBIRED") {
00241       uwbdecider = new DeciderUWBIRED(this, this, syncThreshold, syncAlwaysSucceeds, stats, trace, alwaysFailOnDataInterference);
00242   }
00243   return uwbdecider;
00244 }
00245 
00246 void PhyLayerUWBIR::receiveBBItem(int category, const BBItem *details,
00247     int scopeModuleId) {
00248   Enter_Method_Silent();
00249   ChannelAccess::receiveBBItem(category, details, scopeModuleId);
00250   if (category == catMove) {
00251     coreEV<< "Received move information in uwbphylayer." << endl;
00252 
00253   }
00254 }
00255 
00256 void PhyLayerUWBIR::handleAirFrame(cMessage* msg) {
00257   if (utility->getHostState().get() == HostState::FAILED) {
00258     coreEV<< "host has FAILED, dropping msg " << msg->getName() << endl;
00259     delete msg;
00260     return;
00261   }
00262   BasePhyLayer::handleAirFrame(msg);
00263 }
00264 
00265 void PhyLayerUWBIR::finishRadioSwitching() {
00266   BasePhyLayer::finishRadioSwitching();
00267   setRadioCurrent(radio->getCurrentState());
00268 }
00269 
00270 void PhyLayerUWBIR::handleHostState(const HostState& state) {
00271   // handles only battery consumption
00272 
00273   HostState::States hostState = state.get();
00274 
00275   switch (hostState) {
00276   case HostState::FAILED:
00277     EV<< "t = " << simTime() << " host state FAILED" << endl;
00278     // it would be good to create a radioState OFF, as well
00279     break;
00280   default:
00281     break;
00282   }
00283 }
00284 
00285 void PhyLayerUWBIR::setSwitchingCurrent(int from, int to) {
00286   int act = SWITCHING_ACCT;
00287   double current = 0;
00288 
00289   switch(from) {
00290   case RadioUWBIR::SYNC:
00291   case Radio::RX:
00292     switch(to) {
00293     case Radio::SLEEP:
00294       current = rxCurrent;
00295       break;
00296     case Radio::TX:
00297       current = rxTxCurrent;
00298       break;
00299       // ! transitions between rx and sync should be immediate
00300     default:
00301       opp_error("Unknown radio switch! From RX to %d", to);
00302     }
00303     break;
00304 
00305   case Radio::TX:
00306     switch(to) {
00307     case Radio::SLEEP:
00308       current = txCurrent;
00309       break;
00310     case Radio::RX:
00311       current = txRxCurrent;
00312       break;
00313     default:
00314       opp_error("Unknown radio switch! From TX to %d", to);
00315     }
00316     break;
00317 
00318   case Radio::SLEEP:
00319     switch(to) {
00320     case Radio::TX:
00321       current = setupTxCurrent;
00322       break;
00323     case Radio::RX:
00324       current = setupRxCurrent;
00325       break;
00326     default:
00327       opp_error("Unknown radio switch! From SLEEP to %d", to);
00328     }
00329     break;
00330 
00331   default:
00332     opp_error("Unknown radio state: %d", from);
00333   }
00334 
00335   BatteryAccess::drawCurrent(current, act);
00336 }
00337 
00338 void PhyLayerUWBIR::setRadioCurrent(int rs) {
00339   switch(rs) {
00340   case RadioUWBIR::RX:
00341     BatteryAccess::drawCurrent(rxCurrent, RX_ACCT);
00342     break;
00343   case RadioUWBIR::TX:
00344     BatteryAccess::drawCurrent(txCurrent, TX_ACCT);
00345     break;
00346   case RadioUWBIR::SLEEP:
00347     BatteryAccess::drawCurrent(sleepCurrent, SLEEP_ACCT);
00348     break;
00349   case RadioUWBIR::SYNC:
00350     BatteryAccess::drawCurrent(syncCurrent, SYNC_ACCT);
00351   default:
00352     break;
00353   }
00354 }
00355 
00356 /*
00357 simtime_t PhyLayerUWBIR::setRadioState(int rs) {
00358   if(_radio->getCurrentState()==RadioUWBIR::RX && rs != RadioUWBIR::RX && rs!= RadioUWBIR::SYNC) {
00359     uwbdecider->cancelReception();
00360   }
00361   BasePhyLayer::setRadioState(rs);
00362 }
00363 */
00364 simtime_t PhyLayerUWBIR::setRadioState(int rs) {
00365   int prevState = radio->getCurrentState();
00366 
00367   if(rs==Radio::RX) {
00368     coreEV << "this is my breakpoint" << endl;
00369   }
00370   if(radio->getCurrentState()==RadioUWBIR::RX && rs != RadioUWBIR::RX && rs!= RadioUWBIR::SYNC) {
00371     uwbdecider->cancelReception();
00372   }
00373 
00374   simtime_t endSwitch = BasePhyLayer::setRadioState(rs);
00375 
00376   if(endSwitch >= 0) {
00377     if(radio->getCurrentState() == Radio::SWITCHING) {
00378             setSwitchingCurrent(prevState, rs);
00379     } else {
00380       setRadioCurrent(radio->getCurrentState());
00381     }
00382   }
00383 
00384   return endSwitch;
00385 }
00386 
00387 AirFrame *PhyLayerUWBIR::encapsMsg(cPacket *macPkt)
00388 {
00389   // the cMessage passed must be a MacPacket... but no cast needed here
00390   // MacPkt* pkt = static_cast<MacPkt*>(msg);
00391 
00392   // ...and must always have a ControlInfo attached (contains Signal)
00393   cObject* ctrlInfo = macPkt->removeControlInfo();
00394   assert(ctrlInfo);
00395 
00396   // create the new AirFrame
00397   AirFrameUWBIR* frame = new AirFrameUWBIR("airframe", AIR_FRAME);
00398 
00399   MacToUWBIRPhyControlInfo* macToPhyCI = static_cast<MacToUWBIRPhyControlInfo*>(ctrlInfo);
00400 
00401 
00402 
00403   // Retrieve the pointer to the Signal-instance from the ControlInfo-instance.
00404   // We are now the new owner of this instance.
00405   Signal* s = macToPhyCI->retrieveSignal();
00406   // make sure we really obtained a pointer to an instance
00407   assert(s);
00408 
00409   // put host move pattern to Signal
00410   s->setMove(move);
00411 
00412 
00413   // set the members
00414   assert(s->getSignalLength() > 0);
00415   frame->setDuration(s->getSignalLength());
00416   // copy the signal into the AirFrame
00417   frame->setSignal(*s);
00418   //set priority of AirFrames above the normal priority to ensure
00419   //channel consistency (before any thing else happens at a time
00420   //point t make sure that the channel has removed every AirFrame
00421   //ended at t and added every AirFrame started at t)
00422   frame->setSchedulingPriority(airFramePriority);
00423   frame->setProtocolId(myProtocolId());
00424   frame->setBitLength(headerLength);
00425   frame->setId(world->getUniqueAirFrameId());
00426   frame->setChannel(radio->getCurrentChannel());
00427   frame->setCfg(macToPhyCI->getConfig());
00428 
00429 
00430 
00431   // pointer and Signal not needed anymore
00432   delete s;
00433   s = 0;
00434 
00435 
00436 
00437 
00438   // delete the Control info
00439   delete macToPhyCI;
00440   macToPhyCI = 0;
00441   ctrlInfo = 0;
00442 
00443 
00444   frame->encapsulate(macPkt);
00445 
00446   // --- from here on, the AirFrame is the owner of the MacPacket ---
00447   macPkt = 0;
00448   coreEV <<"AirFrame encapsulated, length: " << frame->getBitLength() << "\n";
00449 
00450   return frame;
00451 }
00452 
00453 
00454 void PhyLayerUWBIR::finish() {
00455   BasePhyLayer::finish();
00456 }
00457