IBR-DTNSuite
0.8
|
00001 #include "core/Node.h" 00002 #include "net/ConvergenceLayer.h" 00003 #include <ibrdtn/utils/Clock.h> 00004 #include <ibrdtn/utils/Utils.h> 00005 #include <ibrcommon/Logger.h> 00006 00007 #include <iostream> 00008 #include <sstream> 00009 00010 using namespace std; 00011 00012 namespace dtn 00013 { 00014 namespace core 00015 { 00016 Node::URI::URI(const Node::Type t, const Node::Protocol p, const std::string &uri, const size_t to, const int prio) 00017 : type(t), protocol(p), value(uri), expire((to == 0) ? 0 : dtn::utils::Clock::getTime() + to), priority(prio) 00018 { 00019 } 00020 00021 Node::URI::~URI() 00022 { 00023 } 00024 00025 void Node::URI::decode(std::string &address, unsigned int &port) const 00026 { 00027 // parse parameters 00028 std::vector<string> parameters = dtn::utils::Utils::tokenize(";", value); 00029 std::vector<string>::const_iterator param_iter = parameters.begin(); 00030 00031 while (param_iter != parameters.end()) 00032 { 00033 std::vector<string> p = dtn::utils::Utils::tokenize("=", (*param_iter)); 00034 00035 if (p[0].compare("ip") == 0) 00036 { 00037 address = p[1]; 00038 } 00039 00040 if (p[0].compare("port") == 0) 00041 { 00042 std::stringstream port_stream; 00043 port_stream << p[1]; 00044 port_stream >> port; 00045 } 00046 00047 param_iter++; 00048 } 00049 } 00050 00051 bool Node::URI::operator<(const URI &other) const 00052 { 00053 if (protocol < other.protocol) return true; 00054 if (protocol != other.protocol) return false; 00055 00056 if (type < other.type) return true; 00057 if (type != other.type) return false; 00058 00059 return (value < other.value); 00060 } 00061 00062 bool Node::URI::operator==(const URI &other) const 00063 { 00064 return ((type == other.type) && (protocol == other.protocol) && (value == other.value)); 00065 } 00066 00067 bool Node::URI::operator==(const Node::Protocol &p) const 00068 { 00069 return (protocol == p); 00070 } 00071 00072 bool Node::URI::operator==(const Node::Type &t) const 00073 { 00074 return (type == t); 00075 } 00076 00077 std::ostream& operator<<(std::ostream &stream, const Node::URI &u) 00078 { 00079 stream << u.priority << "#" << Node::toString(u.type) << "#" << Node::toString(u.protocol) << "#" << u.value; 00080 return stream; 00081 } 00082 00083 Node::Attribute::Attribute(const Type t, const std::string &n, const std::string &v, const size_t to, const int p) 00084 : type(t), name(n), value(v), expire((to == 0) ? 0 : dtn::utils::Clock::getTime() + to), priority(p) 00085 { 00086 } 00087 00088 Node::Attribute::~Attribute() 00089 { 00090 } 00091 00092 bool Node::Attribute::operator<(const Attribute &other) const 00093 { 00094 if (name < other.name) return true; 00095 if (name != other.name) return false; 00096 00097 return (type < other.type); 00098 } 00099 00100 bool Node::Attribute::operator==(const Attribute &other) const 00101 { 00102 return ((type == other.type) && (name == other.name)); 00103 } 00104 00105 bool Node::Attribute::operator==(const std::string &n) const 00106 { 00107 return (name == n); 00108 } 00109 00110 std::ostream& operator<<(std::ostream &stream, const Node::Attribute &a) 00111 { 00112 stream << a.priority << "#" << Node::toString(a.type) << "#" << a.name << "#" << a.value; 00113 return stream; 00114 } 00115 00116 Node::Node() 00117 : _connect_immediately(false), _id() 00118 { 00119 } 00120 00121 Node::Node(const dtn::data::EID &id) 00122 : _connect_immediately(false), _id(id) 00123 { 00124 } 00125 00126 Node::~Node() 00127 { 00128 } 00129 00130 std::string Node::toString(Node::Type type) 00131 { 00132 switch (type) 00133 { 00134 case Node::NODE_UNAVAILABLE: 00135 return "unavailable"; 00136 00137 case Node::NODE_DISCOVERED: 00138 return "discovered"; 00139 00140 case Node::NODE_STATIC: 00141 return "static"; 00142 00143 case Node::NODE_CONNECTED: 00144 return "connected"; 00145 00146 case Node::NODE_DHT_DISCOVERED: 00147 return "dht discovered"; 00148 } 00149 00150 return "unknown"; 00151 } 00152 00153 std::string Node::toString(Node::Protocol proto) 00154 { 00155 switch (proto) 00156 { 00157 case Node::CONN_UNSUPPORTED: 00158 return "unsupported"; 00159 00160 case Node::CONN_UNDEFINED: 00161 return "undefined"; 00162 00163 case Node::CONN_UDPIP: 00164 return "UDP"; 00165 00166 case Node::CONN_TCPIP: 00167 return "TCP"; 00168 00169 case Node::CONN_LOWPAN: 00170 return "LoWPAN"; 00171 00172 case Node::CONN_BLUETOOTH: 00173 return "Bluetooth"; 00174 00175 case Node::CONN_HTTP: 00176 return "HTTP"; 00177 00178 case Node::CONN_FILE: 00179 return "FILE"; 00180 00181 case Node::CONN_DGRAM_UDP: 00182 return "DGRAM:UDP"; 00183 00184 case Node::CONN_DGRAM_ETHERNET: 00185 return "DGRAM:ETHERNET"; 00186 00187 case Node::CONN_DGRAM_LOWPAN: 00188 return "DGRAM:LOWPAN"; 00189 } 00190 00191 return "unknown"; 00192 } 00193 00194 bool Node::has(Node::Protocol proto) const 00195 { 00196 for (std::set<URI>::const_iterator iter = _uri_list.begin(); iter != _uri_list.end(); iter++) 00197 { 00198 if ((*iter) == proto) return true; 00199 } 00200 return false; 00201 } 00202 00203 bool Node::has(const std::string &name) const 00204 { 00205 for (std::set<Attribute>::const_iterator iter = _attr_list.begin(); iter != _attr_list.end(); iter++) 00206 { 00207 if ((*iter) == name) return true; 00208 } 00209 return false; 00210 } 00211 00212 void Node::add(const URI &u) 00213 { 00214 _uri_list.erase(u); 00215 _uri_list.insert(u); 00216 } 00217 00218 void Node::add(const Attribute &attr) 00219 { 00220 _attr_list.erase(attr); 00221 _attr_list.insert(attr); 00222 } 00223 00224 void Node::remove(const URI &u) 00225 { 00226 _uri_list.erase(u); 00227 } 00228 00229 void Node::remove(const Attribute &attr) 00230 { 00231 _attr_list.erase(attr); 00232 } 00233 00234 void Node::clear() 00235 { 00236 _uri_list.clear(); 00237 _attr_list.clear(); 00238 } 00239 00240 // comparison of two URIs according to the priority 00241 bool compare_uri_priority (const Node::URI &first, const Node::URI &second) 00242 { 00243 return first.priority > second.priority; 00244 } 00245 00246 // comparison of two Attributes according to the priority 00247 bool compare_attr_priority (const Node::Attribute &first, const Node::Attribute &second) 00248 { 00249 return first.priority > second.priority; 00250 } 00251 00252 std::list<Node::URI> Node::get(Node::Protocol proto) const 00253 { 00254 std::list<URI> ret; 00255 for (std::set<URI>::const_iterator iter = _uri_list.begin(); iter != _uri_list.end(); iter++) 00256 { 00257 if ((*iter) == proto) 00258 { 00259 ret.push_back(*iter); 00260 } 00261 } 00262 00263 ret.sort(compare_uri_priority); 00264 return ret; 00265 } 00266 00267 std::list<Node::URI> Node::get(Node::Type type, Node::Protocol proto) const 00268 { 00269 std::list<URI> ret; 00270 for (std::set<URI>::const_iterator iter = _uri_list.begin(); iter != _uri_list.end(); iter++) 00271 { 00272 if (((*iter) == proto) && ((*iter) == type)) ret.push_back(*iter); 00273 } 00274 ret.sort(compare_uri_priority); 00275 return ret; 00276 } 00277 00278 std::set<Node::Type> Node::getTypes() const 00279 { 00280 std::set<Type> ret; 00281 for (std::set<URI>::const_iterator iter = _uri_list.begin(); iter != _uri_list.end(); iter++) 00282 { 00283 ret.insert((*iter).type); 00284 } 00285 return ret; 00286 } 00287 00288 std::list<Node::Attribute> Node::get(const std::string &name) const 00289 { 00290 std::list<Attribute> ret; 00291 for (std::set<Attribute>::const_iterator iter = _attr_list.begin(); iter != _attr_list.end(); iter++) 00292 { 00293 if ((*iter) == name) ret.push_back(*iter); 00294 } 00295 ret.sort(compare_attr_priority); 00296 return ret; 00297 } 00298 00299 const dtn::data::EID& Node::getEID() const 00300 { 00301 return _id; 00302 } 00303 00308 bool Node::expire() 00309 { 00310 // get the current timestamp 00311 size_t ct = dtn::utils::Clock::getTime(); 00312 00313 // walk though all Attribute elements and remove the expired ones 00314 { 00315 std::set<Attribute>::iterator iter = _attr_list.begin(); 00316 while ( iter != _attr_list.end() ) 00317 { 00318 const Attribute &attr = (*iter); 00319 if ((attr.expire > 0) && (attr.expire < ct)) 00320 { 00321 // remove this attribute 00322 _attr_list.erase(iter++); 00323 } 00324 else 00325 { 00326 iter++; 00327 } 00328 } 00329 } 00330 00331 // walk though all URI elements and remove the expired ones 00332 { 00333 std::set<URI>::iterator iter = _uri_list.begin(); 00334 while ( iter != _uri_list.end() ) 00335 { 00336 const URI &u = (*iter); 00337 if ((u.expire > 0) && (u.expire < ct)) 00338 { 00339 // remove this attribute 00340 _uri_list.erase(iter++); 00341 } 00342 else 00343 { 00344 iter++; 00345 } 00346 } 00347 } 00348 00349 return (_attr_list.empty() && _uri_list.empty()); 00350 } 00351 00352 const Node& Node::operator+=(const Node &other) 00353 { 00354 for (std::set<Attribute>::const_iterator iter = other._attr_list.begin(); iter != other._attr_list.end(); iter++) 00355 { 00356 const Attribute &attr = (*iter); 00357 add(attr); 00358 } 00359 00360 for (std::set<URI>::const_iterator iter = other._uri_list.begin(); iter != other._uri_list.end(); iter++) 00361 { 00362 const URI &u = (*iter); 00363 add(u); 00364 } 00365 00366 return (*this); 00367 } 00368 00369 const Node& Node::operator-=(const Node &other) 00370 { 00371 for (std::set<Attribute>::const_iterator iter = other._attr_list.begin(); iter != other._attr_list.end(); iter++) 00372 { 00373 const Attribute &attr = (*iter); 00374 remove(attr); 00375 } 00376 00377 for (std::set<URI>::const_iterator iter = other._uri_list.begin(); iter != other._uri_list.end(); iter++) 00378 { 00379 const URI &u = (*iter); 00380 remove(u); 00381 } 00382 00383 return (*this); 00384 } 00385 00386 bool Node::operator==(const dtn::data::EID &other) const 00387 { 00388 return (other == _id); 00389 } 00390 00391 bool Node::operator==(const Node &other) const 00392 { 00393 return (other._id == _id); 00394 } 00395 00396 bool Node::operator<(const Node &other) const 00397 { 00398 if (_id < other._id ) return true; 00399 00400 return false; 00401 } 00402 00403 std::string Node::toString() const 00404 { 00405 std::stringstream ss; ss << getEID().getString(); 00406 return ss.str(); 00407 } 00408 00409 bool Node::doConnectImmediately() const 00410 { 00411 return _connect_immediately; 00412 } 00413 00414 void Node::setConnectImmediately(bool val) 00415 { 00416 _connect_immediately = val; 00417 } 00418 00419 bool Node::isAvailable() const 00420 { 00421 return !_uri_list.empty(); 00422 } 00423 00424 std::ostream& operator<<(std::ostream &stream, const Node &node) 00425 { 00426 stream << "Node: " << node._id.getString() << " [ "; 00427 for (std::set<Node::Attribute>::const_iterator iter = node._attr_list.begin(); iter != node._attr_list.end(); iter++) 00428 { 00429 const Node::Attribute &attr = (*iter); 00430 stream << attr << "#expire=" << attr.expire << "; "; 00431 } 00432 00433 for (std::set<Node::URI>::const_iterator iter = node._uri_list.begin(); iter != node._uri_list.end(); iter++) 00434 { 00435 const Node::URI &u = (*iter); 00436 stream << u << "#expire=" << u.expire << "; "; 00437 } 00438 stream << " ]"; 00439 00440 return stream; 00441 } 00442 } 00443 }