Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008 #include "routing/RetransmissionExtension.h"
00009 #include "core/TimeEvent.h"
00010 #include "routing/RequeueBundleEvent.h"
00011 #include "net/TransferAbortedEvent.h"
00012 #include "net/TransferCompletedEvent.h"
00013 #include "core/BundleExpiredEvent.h"
00014 #include "ibrdtn/utils/Clock.h"
00015 #include "ibrdtn/data/Exceptions.h"
00016
00017 namespace dtn
00018 {
00019 namespace routing
00020 {
00021 RetransmissionExtension::RetransmissionExtension()
00022 {
00023 }
00024
00025 RetransmissionExtension::~RetransmissionExtension()
00026 {
00027 }
00028
00029 void RetransmissionExtension::notify(const dtn::core::Event *evt)
00030 {
00031 try {
00032 const dtn::core::TimeEvent &time = dynamic_cast<const dtn::core::TimeEvent&>(*evt);
00033
00034 if (!_queue.empty())
00035 {
00036 const RetransmissionData &data = _queue.front();
00037
00038 if ( data.getTimestamp() <= time.getTimestamp() )
00039 {
00040
00041 getRouter()->transferTo(data.destination, data);
00042
00043
00044 _queue.pop();
00045 }
00046 }
00047 return;
00048 } catch (std::bad_cast ex) { };
00049
00050 try {
00051 const dtn::net::TransferCompletedEvent &completed = dynamic_cast<const dtn::net::TransferCompletedEvent&>(*evt);
00052
00053
00054 RetransmissionData data(completed.getBundle(), completed.getPeer());
00055 _set.erase(data);
00056
00057 return;
00058 } catch (std::bad_cast ex) { };
00059
00060 try {
00061 const dtn::net::TransferAbortedEvent &aborted = dynamic_cast<const dtn::net::TransferAbortedEvent&>(*evt);
00062
00063
00064 RetransmissionData data(aborted.getBundleID(), aborted.getPeer());
00065 _set.erase(data);
00066
00067 return;
00068 } catch (std::bad_cast ex) { };
00069
00070 try {
00071 const dtn::routing::RequeueBundleEvent &requeue = dynamic_cast<const dtn::routing::RequeueBundleEvent&>(*evt);
00072
00073 const RetransmissionData data(requeue._bundle, requeue._peer);
00074 std::set<RetransmissionData>::const_iterator iter = _set.find(data);
00075
00076 if (iter != _set.end())
00077 {
00078
00079 RetransmissionData data2 = (*iter);
00080 data2++;
00081
00082
00083 _set.erase(data);
00084
00085 if (data2.getCount() <= 10)
00086 {
00087
00088 _set.insert(data2);
00089 _queue.push(data2);
00090 }
00091 else
00092 {
00093 dtn::net::TransferAbortedEvent::raise(requeue._peer, requeue._bundle, dtn::net::TransferAbortedEvent::REASON_RETRY_LIMIT_REACHED);
00094 }
00095 }
00096 else
00097 {
00098
00099 _set.insert(data);
00100 _queue.push(data);
00101 }
00102
00103 return;
00104 } catch (std::bad_cast ex) { };
00105
00106 try {
00107 const dtn::core::BundleExpiredEvent &expired = dynamic_cast<const dtn::core::BundleExpiredEvent&>(*evt);
00108
00109
00110 size_t elements = _queue.size();
00111 for (size_t i = 0; i < elements; i++)
00112 {
00113 const RetransmissionData &data = _queue.front();
00114
00115 if ((dtn::data::BundleID&)data == expired._bundle)
00116 {
00117 dtn::net::TransferAbortedEvent::raise(data.destination, data, dtn::net::TransferAbortedEvent::REASON_BUNDLE_DELETED);
00118 }
00119 else
00120 {
00121 _queue.push(data);
00122 }
00123
00124 _queue.pop();
00125 }
00126
00127 return;
00128 } catch (std::bad_cast ex) { };
00129 }
00130
00131 bool RetransmissionExtension::RetransmissionData::operator!=(const RetransmissionData &obj)
00132 {
00133 const dtn::data::BundleID &id1 = dynamic_cast<const dtn::data::BundleID&>(obj);
00134 const dtn::data::BundleID &id2 = dynamic_cast<const dtn::data::BundleID&>(*this);
00135
00136 if (id1 != id2) return true;
00137 if (obj.destination != destination) return true;
00138
00139 return false;
00140 }
00141
00142 bool RetransmissionExtension::RetransmissionData::operator==(const RetransmissionData &obj)
00143 {
00144 const dtn::data::BundleID &id1 = dynamic_cast<const dtn::data::BundleID&>(obj);
00145 const dtn::data::BundleID &id2 = dynamic_cast<const dtn::data::BundleID&>(*this);
00146
00147 if (id1 != id2) return false;
00148 if (obj.destination != destination) return false;
00149
00150 return true;
00151 }
00152
00153 size_t RetransmissionExtension::RetransmissionData::getCount() const
00154 {
00155 return _count;
00156 }
00157
00158 size_t RetransmissionExtension::RetransmissionData::getTimestamp() const
00159 {
00160 return _timestamp;
00161 }
00162
00163 RetransmissionExtension::RetransmissionData& RetransmissionExtension::RetransmissionData::operator++(int)
00164 {
00165 _count++;
00166 _timestamp = dtn::utils::Clock::getTime();
00167 _timestamp += retry;
00168
00169 return (*this);
00170 }
00171
00172 RetransmissionExtension::RetransmissionData& RetransmissionExtension::RetransmissionData::operator++()
00173 {
00174 _count++;
00175 _timestamp = dtn::utils::Clock::getTime();
00176 _timestamp += retry;
00177
00178 return (*this);
00179 }
00180
00181 RetransmissionExtension::RetransmissionData::RetransmissionData(const dtn::data::BundleID &id, dtn::data::EID d, size_t r)
00182 : dtn::data::BundleID(id), destination(d), _timestamp(0), _count(0), retry(r)
00183 {
00184 (*this)++;
00185 }
00186
00187 RetransmissionExtension::RetransmissionData::~RetransmissionData()
00188 {
00189 }
00190 }
00191 }