DHTDataStorage.cc

Go to the documentation of this file.
00001 //
00002 // Copyright (C) 2007 Institut fuer Telematik, Universitaet Karlsruhe (TH)
00003 //
00004 // This program is free software; you can redistribute it and/or
00005 // modify it under the terms of the GNU General Public License
00006 // as published by the Free Software Foundation; either version 2
00007 // of the License, or (at your option) any later version.
00008 //
00009 // This program is distributed in the hope that it will be useful,
00010 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00011 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012 // GNU General Public License for more details.
00013 //
00014 // You should have received a copy of the GNU General Public License
00015 // along with this program; if not, write to the Free Software
00016 // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
00017 //
00018 
00024 #include <omnetpp.h>
00025 #include <hashWatch.h>
00026 
00027 #include "DHTDataStorage.h"
00028 
00029 Define_Module(DHTDataStorage);
00030 
00031 using namespace std;
00032 
00033 std::ostream& operator<<(std::ostream& Stream, const DhtDataEntry entry)
00034 {
00035     return Stream << "Value: " << entry.value
00036                   << " Kind: " << entry.kind
00037                   << " ID: " << entry.id
00038                   << " Endtime: " << entry.ttlMessage->getArrivalTime()
00039                   << " Modifiable: " << entry.is_modifiable
00040                   << " SourceNode: " << entry.sourceNode;
00041 }
00042 
00043 
00044 void DHTDataStorage::initialize(int stage)
00045 {
00046     if (stage != MIN_STAGE_APP)
00047         return;
00048 
00049     WATCH_MULTIMAP(dataMap);
00050 }
00051 
00052 void DHTDataStorage::handleMessage(cMessage* msg)
00053 {
00054     error("This module doesn't handle messages!");
00055 }
00056 
00057 void DHTDataStorage::clear()
00058 {
00059     map<OverlayKey, DhtDataEntry>::iterator iter;
00060 
00061     for( iter = dataMap.begin(); iter != dataMap.end(); iter++ ) {
00062         cancelAndDelete(iter->second.ttlMessage);
00063     }
00064 
00065     dataMap.clear();
00066 }
00067 
00068 
00069 uint32_t DHTDataStorage::getSize()
00070 {
00071     return dataMap.size();
00072 }
00073 
00074 DhtDataEntry* DHTDataStorage::getDataEntry(const OverlayKey& key,
00075                                            uint32_t kind, uint32_t id)
00076 {
00077     pair<DhtDataMap::iterator, DhtDataMap::iterator> pos =
00078         dataMap.equal_range(key);
00079 
00080     while (pos.first != pos.second) {
00081         if ((pos.first->second.kind == kind) &&
00082                 (pos.first->second.id == id)) {
00083             return &pos.first->second;
00084         }
00085         ++pos.first;
00086     }
00087 
00088     return NULL;
00089 }
00090 
00091 
00092 
00093 DhtDataVector* DHTDataStorage::getDataVector(const OverlayKey& key,
00094                                              uint32_t kind, uint32_t id)
00095 {
00096     DhtDataVector* vect = new DhtDataVector();
00097     DhtDataEntry entry;
00098 
00099     pair<DhtDataMap::iterator, DhtDataMap::iterator> pos =
00100         dataMap.equal_range(key);
00101 
00102     while (pos.first != pos.second) {
00103         entry = pos.first->second;
00104         vect->push_back(make_pair(key, entry));
00105         ++pos.first;
00106     }
00107 
00108     return vect;
00109 }
00110 
00111 
00112 const NodeHandle& DHTDataStorage::getSourceNode(const OverlayKey& key,
00113                                                 uint32_t kind, uint32_t id)
00114 {
00115     DhtDataEntry* entry = getDataEntry(key, kind, id);
00116 
00117     if (entry == NULL)
00118         return NodeHandle::UNSPECIFIED_NODE;
00119     else
00120         return entry->sourceNode;
00121 }
00122 
00123 const bool DHTDataStorage::isModifiable(const OverlayKey& key,
00124                                         uint32_t kind, uint32_t id)
00125 {
00126     DhtDataEntry* entry = getDataEntry(key, kind, id);
00127 
00128     if (entry == NULL)
00129         return true;
00130     else
00131         return entry->is_modifiable;
00132 }
00133 
00134 
00135 const DhtDataMap::iterator DHTDataStorage::begin()
00136 {
00137     return dataMap.begin();
00138 }
00139 
00140 
00141 void DHTDataStorage::addData(const OverlayKey& key, uint32_t kind, uint32_t id,
00142                              BinaryValue value, cMessage* ttlMessage,
00143                              bool is_modifiable, NodeHandle sourceNode,
00144                              bool responsible)
00145 {
00146     DhtDataEntry entry;
00147     entry.kind = kind;
00148     entry.id = id;
00149     entry.value = value;
00150     entry.ttlMessage = ttlMessage;
00151     entry.sourceNode = sourceNode;
00152     entry.is_modifiable = is_modifiable;
00153     entry.responsible = responsible;
00154 
00155     if ((kind == 0) || (id == 0)) {
00156         throw cRuntimeError("DHTDataStorage::addData(): "
00157                             "Not allowed to add data with kind = 0 or id = 0!");
00158     }
00159 
00160     pair<DhtDataMap::iterator, DhtDataMap::iterator> pos =
00161         dataMap.equal_range(key);
00162 
00163     // insert new record in sorted multimap (order: key, kind, id)
00164     while ((pos.first != pos.second) && (pos.first->second.kind < kind)) {
00165         ++pos.first;
00166     }
00167 
00168     while ((pos.first != pos.second) && (pos.first->second.kind == kind)
00169             && (pos.first->second.id < id)) {
00170         ++pos.first;
00171     }
00172 
00173     dataMap.insert(pos.first, make_pair(key, entry));
00174 }
00175 
00176 void DHTDataStorage::removeData(const OverlayKey& key, uint32_t kind,
00177                                 uint32_t id)
00178 {
00179     pair<DhtDataMap::iterator, DhtDataMap::iterator> pos =
00180         dataMap.equal_range(key);
00181 
00182     while (pos.first != pos.second) {
00183 
00184         if (((kind == 0) || (pos.first->second.kind == kind)) &&
00185                 ((id == 0) || (pos.first->second.id == id))) {
00186             cancelAndDelete(pos.first->second.ttlMessage);
00187             dataMap.erase(pos.first++);
00188         } else {
00189             ++pos.first;
00190         }
00191     }
00192 }
00193 
00194 DhtDumpVector* DHTDataStorage::dumpDht(const OverlayKey& key, uint32_t kind,
00195                                        uint32_t id)
00196 {
00197     DhtDumpVector* vect = new DhtDumpVector();
00198     DhtDumpEntry entry;
00199 
00200     DhtDataMap::iterator iter, end;
00201 
00202     if (key.isUnspecified()) {
00203         iter = dataMap.begin();
00204         end = dataMap.end();
00205     } else {
00206         iter = dataMap.lower_bound(key);
00207         end = dataMap.upper_bound(key);
00208     }
00209 
00210     for (; iter != end; iter++) {
00211         if (((kind == 0) || (iter->second.kind == kind)) &&
00212                 ((id == 0) || (iter->second.id == id))) {
00213 
00214             entry.setKey(iter->first);
00215             entry.setKind(iter->second.kind);
00216             entry.setId(iter->second.id);
00217             entry.setValue(iter->second.value);
00218             entry.setTtl((int)SIMTIME_DBL(
00219                         iter->second.ttlMessage->getArrivalTime() - simTime()));
00220             entry.setOwnerNode(iter->second.sourceNode);
00221             entry.setIs_modifiable(iter->second.is_modifiable);
00222             entry.setResponsible(iter->second.responsible);
00223             vect->push_back(entry);
00224         }
00225     }
00226 
00227     return vect;
00228 }
00229 
00230 
00231 // TODO: not used ?
00232 void DHTDataStorage::updateDisplayString()
00233 {
00234     if (ev.isGUI()) {
00235         char buf[80];
00236 
00237         if (dataMap.size() == 1) {
00238             sprintf(buf, "1 data item");
00239         } else {
00240             sprintf(buf, "%zi data items", dataMap.size());
00241         }
00242 
00243         getDisplayString().setTagArg("t", 0, buf);
00244         getDisplayString().setTagArg("t", 2, "blue");
00245     }
00246 
00247 }
00248 
00249 // TODO: not used ?
00250 void DHTDataStorage::updateTooltip()
00251 {
00252     if (ev.isGUI()) {
00253         std::stringstream str;
00254 
00255         for (DhtDataMap::iterator it = dataMap.begin();
00256              it != dataMap.end(); it++) {
00257             str << it->second.value;
00258         }
00259 
00260         str << endl;
00261 
00262         char buf[1024];
00263         sprintf(buf, "%s", str.str().c_str());
00264         getDisplayString().setTagArg("tt", 0, buf);
00265     }
00266 }
00267 
00268 // TODO: not used ?
00269 void DHTDataStorage::display()
00270 {
00271     cout << "Content of DHTDataStorage:" << endl;
00272     for (DhtDataMap::iterator it = dataMap.begin();
00273          it != dataMap.end(); it++) {
00274         cout << "Key: " << it->first << " Kind: " << it->second.kind
00275              << " ID: " << it->second.id << " Value: "
00276              << it->second.value << "End-time: "
00277              << it->second.ttlMessage->getArrivalTime() << endl;
00278     }
00279 }

Generated on Tue Sep 8 17:26:52 2009 for OverSim by  doxygen 1.5.8