Decider80211.cc

00001 /*
00002  * Decider80211.cc
00003  *
00004  *  Created on: 11.02.2009
00005  *      Author: karl wessel
00006  */
00007 
00008 #include "Decider80211.h"
00009 #include <DeciderResult80211.h>
00010 #include <Mac80211Pkt_m.h>
00011 
00012 Decider80211::Decider80211( DeciderToPhyInterface* phy,
00013               double threshold,
00014               double sensitivity,
00015               int channel,
00016               int myIndex,
00017               bool debug):
00018   BaseDecider(phy, sensitivity, myIndex, debug),
00019   snrThreshold(threshold)
00020 {
00021   assert(1 <= channel);
00022   assert(channel  <= 14);
00023   centerFrequency = CENTER_FREQUENCIES[channel];
00024 }
00025 
00026 simtime_t Decider80211::processNewSignal(AirFrame* frame) {
00027   if(currentSignal.first != 0) {
00028     deciderEV << "Already receiving another AirFrame!" << endl;
00029     return notAgain;
00030   }
00031 
00032   // get the receiving power of the Signal at start-time and center frequency
00033   Signal& signal = frame->getSignal();
00034   Argument start(DimensionSet::timeFreqDomain);
00035   start.setTime(signal.getSignalStart());
00036   start.setArgValue(Dimension::frequency_static(), centerFrequency);
00037 
00038   double recvPower = signal.getReceivingPower()->getValue(start);
00039 
00040   // check whether signal is strong enough to receive
00041   if ( recvPower < sensitivity )
00042   {
00043     deciderEV << "Signal is to weak (" << recvPower << " < " << sensitivity
00044         << ") -> do not receive." << endl;
00045     // Signal too weak, we can't receive it, tell PhyLayer that we don't want it again
00046     return notAgain;
00047   }
00048 
00049   // Signal is strong enough, receive this Signal and schedule it
00050   deciderEV << "Signal is strong enough (" << recvPower << " > " << sensitivity
00051       << ") -> Trying to receive AirFrame." << endl;
00052 
00053   currentSignal.first = frame;
00054   currentSignal.second = EXPECT_END;
00055 
00056   //channel turned busy
00057   setChannelIdleStatus(false);
00058 
00059   return ( signal.getSignalStart() + signal.getSignalLength() );
00060 }
00061 
00062 double Decider80211::calcChannelSenseRSSI(simtime_t start, simtime_t end) {
00063   Mapping* rssiMap = calculateRSSIMapping(start, end);
00064 
00065   Argument min(DimensionSet::timeFreqDomain);
00066   min.setTime(start);
00067   min.setArgValue(Dimension::frequency_static(), centerFrequency - 11e6);
00068   Argument max(DimensionSet::timeFreqDomain);
00069   max.setTime(end);
00070   max.setArgValue(Dimension::frequency_static(), centerFrequency + 11e6);
00071 
00072   double rssi = MappingUtils::findMax(*rssiMap, min, max);
00073 
00074   delete rssiMap;
00075 
00076   return rssi;
00077 }
00078 
00079 
00080 DeciderResult* Decider80211::checkIfSignalOk(AirFrame* frame)
00081 {
00082   // check if the snrMapping is above the Decider's specific threshold,
00083   // i.e. the Decider has received it correctly
00084 
00085   // first collect all necessary information
00086   Mapping* snrMap = calculateSnrMapping(frame);
00087   assert(snrMap);
00088 
00089   Signal& s = frame->getSignal();
00090   simtime_t start = s.getSignalStart();
00091   simtime_t end = start + s.getSignalLength();
00092 
00093   start = start + RED_PHY_HEADER_DURATION; //its ok if the phy header is received only
00094                        //partly - TODO: maybe solve this nicer
00095   Argument min(DimensionSet::timeFreqDomain);
00096   min.setTime(start);
00097   min.setArgValue(Dimension::frequency_static(), centerFrequency - 11e6);
00098   Argument max(DimensionSet::timeFreqDomain);
00099   max.setTime(end);
00100   max.setArgValue(Dimension::frequency_static(), centerFrequency + 11e6);
00101 
00102   double snirMin = MappingUtils::findMin(*snrMap, min, max);
00103 
00104   deciderEV << " snrMin: " << snirMin << endl;
00105 
00106   ConstMappingIterator* bitrateIt = s.getBitrate()->createConstIterator();
00107   bitrateIt->next(); //iterate to payload bitrate indicator
00108   double payloadBitrate = bitrateIt->getValue();
00109   delete bitrateIt;
00110 
00111   DeciderResult80211* result = 0;
00112 
00113   if (snirMin > snrThreshold) {
00114     if(packetOk(snirMin, frame->getBitLength() - (int)PHY_HEADER_LENGTH, payloadBitrate)) {
00115       result = new DeciderResult80211(true, payloadBitrate, snirMin);
00116     } else {
00117       deciderEV << "Packet has BIT ERRORS! It is lost!\n";
00118       result = new DeciderResult80211(false, payloadBitrate, snirMin);
00119     }
00120   } else {
00121     deciderEV << "Packet has ERRORS! It is lost!\n";
00122     result = new DeciderResult80211(false, payloadBitrate, snirMin);
00123   }
00124 
00125   delete snrMap;
00126   snrMap = 0;
00127 
00128   return result;
00129 }
00130 
00131 bool Decider80211::packetOk(double snirMin, int lengthMPDU, double bitrate)
00132 {
00133     double berHeader, berMPDU;
00134 
00135     berHeader = 0.5 * exp(-snirMin * BANDWIDTH / BITRATE_HEADER);
00136     //if PSK modulation
00137     if (bitrate == 1E+6 || bitrate == 2E+6) {
00138         berMPDU = 0.5 * exp(-snirMin * BANDWIDTH / bitrate);
00139     }
00140     //if CCK modulation (modeled with 16-QAM)
00141     else if (bitrate == 5.5E+6) {
00142         berMPDU = 2.0 * (1.0 - 1.0 / sqrt(pow(2.0, 4))) * erfc(sqrt(2.0*snirMin * BANDWIDTH / bitrate));
00143     }
00144     else {                       // CCK, modelled with 256-QAM
00145         berMPDU = 2.0 * (1.0 - 1.0 / sqrt(pow(2.0, 8))) * erfc(sqrt(2.0*snirMin * BANDWIDTH / bitrate));
00146     }
00147 
00148     //probability of no bit error in the PLCP header
00149     double headerNoError = pow(1.0 - berHeader, HEADER_WITHOUT_PREAMBLE);
00150 
00151     //probability of no bit error in the MPDU
00152     double MpduNoError = pow(1.0 - berMPDU, lengthMPDU);
00153     deciderEV << "berHeader: " << berHeader << " berMPDU: " << berMPDU << endl;
00154     double rand = dblrand();
00155 
00156     //if error in header
00157     if (rand > headerNoError)
00158         return (false);
00159     else
00160     {
00161         rand = dblrand();
00162 
00163         //if error in MPDU
00164         if (rand > MpduNoError)
00165             return (false);
00166         //if no error
00167         else
00168             return (true);
00169     }
00170 }
00171 
00172 simtime_t Decider80211::processSignalEnd(AirFrame* frame)
00173 {
00174   // here the Signal is finally processed
00175 
00176   DeciderResult* result = checkIfSignalOk(frame);
00177 
00178   if (result->isSignalCorrect())
00179   {
00180     deciderEV << "packet was received correctly, it is now handed to upper layer...\n";
00181     // go on with processing this AirFrame, send it to the Mac-Layer
00182     phy->sendUp(frame, result);
00183   } else
00184   {
00185     deciderEV << "packet was not received correctly, sending it as control message to upper layer\n";
00186     Mac80211Pkt* mac = static_cast<Mac80211Pkt*>(frame->decapsulate());
00187     mac->setName("ERROR");
00188     mac->setKind(BITERROR);
00189     phy->sendControlMsg(mac);
00190     delete result;
00191   }
00192 
00193   // we have processed this AirFrame and we prepare to receive the next one
00194   currentSignal.first = 0;
00195 
00196   //channel is idle now
00197   setChannelIdleStatus(true);
00198 
00199   return notAgain;
00200 }