00001 #include "ChannelInfo.h"
00002
00003 #include <iostream>
00004 #include <assert.h>
00005
00006 void ChannelInfo::addAirFrame(AirFrame* frame, simtime_t startTime)
00007 {
00008 assert(airFrameStarts.count(frame) == 0);
00009
00010
00011 if(isChannelEmpty()) {
00012
00013 earliestInfoPoint = startTime;
00014 }
00015
00016
00017 simtime_t endTime = startTime + frame->getDuration();
00018
00019
00020 activeAirFrames[endTime].push_back(AirFrameTimePair(startTime, frame));
00021
00022
00023 airFrameStarts[frame] = startTime;
00024
00025 assert(!isChannelEmpty());
00026 }
00027
00028 simtime_t ChannelInfo::findEarliestInfoPoint()
00029 {
00030
00031
00032
00033 simtime_t earliestStart = 0;
00034 AirFrameStartMap::const_iterator it = airFrameStarts.begin();
00035
00036
00037 if (it != airFrameStarts.end())
00038 {
00039
00040 earliestStart = (*it).second;
00041
00042
00043 for (; it != airFrameStarts.end(); ++it)
00044 {
00045
00046
00047 if( (*it).second < earliestStart )
00048 earliestStart = (*it).second;
00049 }
00050 }
00051
00052 return earliestStart;
00053 }
00054
00055 simtime_t ChannelInfo::removeAirFrame(AirFrame* frame)
00056 {
00057 assert(airFrameStarts.count(frame) > 0);
00058
00059
00060 simtime_t startTime = airFrameStarts[frame];
00061
00062
00063 simtime_t endTime = startTime + frame->getDuration();
00064
00065
00066 deleteAirFrame(activeAirFrames, frame, startTime, endTime);
00067
00068
00069 addToInactives(frame, startTime, endTime);
00070
00071
00072
00073
00074 if(isChannelEmpty()) {
00075 earliestInfoPoint = -1;
00076 } else {
00077 earliestInfoPoint = findEarliestInfoPoint();
00078 }
00079
00080 return earliestInfoPoint;
00081 }
00082
00083 void ChannelInfo::assertNoIntersections() {
00084 for(AirFrameMatrix::iterator it1 = inactiveAirFrames.begin();
00085 it1 != inactiveAirFrames.end(); ++it1)
00086 {
00087 simtime_t e0 = it1->first;
00088 for(AirFrameTimeList::iterator it2 = it1->second.begin();
00089 it2 != it1->second.end(); ++it2)
00090 {
00091 simtime_t s0 = it2->first;
00092
00093 bool intersects = (recordStartTime > -1 && recordStartTime <= e0);
00094
00095 for(AirFrameMatrix::iterator it3 = activeAirFrames.begin();
00096 it3 != activeAirFrames.end() && !intersects; ++it3)
00097 {
00098 simtime_t e1 = it3->first;
00099 for(AirFrameTimeList::iterator it4 = it3->second.begin();
00100 it4 != it3->second.end() && !intersects; ++it4)
00101 {
00102 simtime_t s1 = it4->first;
00103
00104 if(e0 >= s1 && s0 <= e1)
00105 intersects = true;
00106 }
00107 }
00108 assert(intersects);
00109 }
00110 }
00111 }
00112
00113 void ChannelInfo::deleteAirFrame(AirFrameMatrix& airFrames,
00114 AirFrame* frame,
00115 simtime_t startTime, simtime_t endTime)
00116 {
00117 AirFrameMatrix::iterator listIt = airFrames.find(endTime);
00118 AirFrameTimeList* list = &listIt->second;
00119
00120 for(AirFrameTimeList::iterator it = list->begin();
00121 it != list->end(); it++)
00122 {
00123 if(it->second == frame)
00124 {
00125 it = list->erase(it);
00126 if(list->empty()) {
00127 airFrames.erase(listIt);
00128 }
00129 return;
00130 }
00131 }
00132
00133 assert(false);
00134 }
00135
00136 bool ChannelInfo::canDiscardInterval(simtime_t startTime,
00137 simtime_t endTime)
00138 {
00139 assert(recordStartTime >= 0 || recordStartTime == -1);
00140
00141
00142
00143
00144 return (recordStartTime > endTime || recordStartTime == -1)
00145 && !isIntersecting(activeAirFrames, startTime, endTime);
00146 }
00147
00148 void ChannelInfo::checkAndCleanInterval(simtime_t startTime,
00149 simtime_t endTime)
00150 {
00151
00152
00153
00154 IntersectionIterator inactiveIntersectIt(&inactiveAirFrames,
00155 startTime,
00156 endTime);
00157
00158 AirFrame* inactiveIntersect = inactiveIntersectIt.next();
00159 while(inactiveIntersect != 0)
00160 {
00161 simtime_t currentStart = airFrameStarts[inactiveIntersect];
00162 simtime_t currentEnd = currentStart + inactiveIntersect->getDuration();
00163
00164 if(canDiscardInterval(currentStart, currentEnd))
00165 {
00166 inactiveIntersectIt.eraseAirFrame();
00167
00168 airFrameStarts.erase(inactiveIntersect);
00169
00170 delete inactiveIntersect;
00171 inactiveIntersect = 0;
00172 }
00173 inactiveIntersect = inactiveIntersectIt.next();
00174 }
00175 }
00176
00177 void ChannelInfo::addToInactives(AirFrame* frame,
00178 simtime_t startTime,
00179 simtime_t endTime)
00180 {
00181
00182
00183 checkAndCleanInterval(startTime, endTime);
00184
00185 if(!canDiscardInterval(startTime, endTime))
00186 {
00187 inactiveAirFrames[endTime].push_back(AirFrameTimePair(startTime, frame));
00188 }
00189 else
00190 {
00191 airFrameStarts.erase(frame);
00192
00193 delete frame;
00194 }
00195 }
00196
00197 bool ChannelInfo::isIntersecting(const AirFrameMatrix& airFrames,
00198 simtime_t from, simtime_t to) const
00199 {
00200 ConstIntersectionIterator it(&airFrames, from, to);
00201 return (it.next() != 0);
00202 }
00203
00204 void ChannelInfo::getIntersections( const AirFrameMatrix& airFrames,
00205 simtime_t from, simtime_t to,
00206 AirFrameVector& outVector) const
00207 {
00208 ConstIntersectionIterator it(&airFrames, from, to);
00209
00210 AirFrame* intersect = it.next();
00211 while(intersect != 0)
00212 {
00213 outVector.push_back(intersect);
00214 intersect = it.next();
00215 }
00216 }
00217
00218 void ChannelInfo::getAirFrames(simtime_t from, simtime_t to,
00219 AirFrameVector& out) const
00220 {
00221
00222 getIntersections(inactiveAirFrames, from, to, out);
00223
00224
00225 getIntersections(activeAirFrames, from, to, out);
00226 }
00227
00228