00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00024 #include <IPAddressResolver.h>
00025
00026 #include "CBR-DHT.h"
00027
00028 #include <RpcMacros.h>
00029 #include <BaseRpc.h>
00030 #include <GlobalStatistics.h>
00031 #include <CoordBasedRoutingAccess.h>
00032 #include <NeighborCache.h>
00033
00034 Define_Module(CBRDHT);
00035
00036 using namespace std;
00037
00038 CBRDHT::CBRDHT()
00039 {
00040 dataStorage = NULL;
00041 }
00042
00043 CBRDHT::~CBRDHT()
00044 {
00045 std::map<unsigned int, BaseCallMessage*>::iterator it;
00046
00047 for (it = rpcIdMap.begin(); it != rpcIdMap.end(); it++) {
00048 delete it->second;
00049 it->second = NULL;
00050 }
00051
00052 std::map<int, GetMapEntry>::iterator it2;
00053 for (it2 = getMap.begin(); it2 != getMap.end(); it2++) {
00054
00055 delete it2->second.callMsg;
00056 it2->second.callMsg = NULL;
00057 }
00058
00059 std::map<int, PutMapEntry>::iterator it3;
00060
00061 for (it3 = putMap.begin(); it3 != putMap.end(); it3++) {
00062
00063
00064
00065 delete it3->second.callMsg;
00066 it3->second.callMsg = NULL;
00067 }
00068
00069 rpcIdMap.clear();
00070 getMap.clear();
00071 putMap.clear();
00072
00073 if (dataStorage != NULL) {
00074 dataStorage->clear();
00075 }
00076 }
00077
00078 void CBRDHT::initializeApp(int stage)
00079 {
00080 if (stage != MIN_STAGE_APP)
00081 return;
00082
00083 dataStorage = check_and_cast<DHTDataStorage*>
00084 (getParentModule()->getSubmodule("dhtDataStorage"));
00085
00086 coordBasedRouting = CoordBasedRoutingAccess().get();
00087 neighborCache = (NeighborCache*)getParentModule()
00088 ->getParentModule()->getSubmodule("neighborCache");
00089
00090 numReplica = par("numReplica");
00091 numReplicaTeams = par("numReplicaTeams");
00092
00093 if (numReplica > numReplicaTeams * overlay->getMaxNumSiblings()) {
00094 opp_error("DHT::initialize(): numReplica bigger than what this "
00095 "overlay can handle (%d)", numReplicaTeams*overlay->getMaxNumSiblings());
00096 }
00097
00098 maintenanceMessages = 0;
00099 normalMessages = 0;
00100 numBytesMaintenance = 0;
00101 numBytesNormal = 0;
00102 WATCH(maintenanceMessages);
00103 WATCH(normalMessages);
00104 WATCH(numBytesNormal);
00105 WATCH(numBytesMaintenance);
00106 WATCH_MAP(rpcIdMap);
00107 }
00108
00109 void CBRDHT::handleTimerEvent(cMessage* msg)
00110 {
00111 DHTTtlTimer* msg_timer = dynamic_cast<DHTTtlTimer*> (msg);
00112
00113 if (msg_timer) {
00114 EV << "[DHT::handleTimerEvent()]\n"
00115 << " received timer ttl, key: "
00116 << msg_timer->getKey().toString(16)
00117 << "\n (overlay->getThisNode().key = "
00118 << overlay->getThisNode().getKey().toString(16) << ")"
00119 << endl;
00120
00121 dataStorage->removeData(msg_timer->getKey(), msg_timer->getKind(),
00122 msg_timer->getId());
00123
00124 }
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141 }
00142
00143 bool CBRDHT::handleRpcCall(BaseCallMessage* msg)
00144 {
00145
00146 RPC_SWITCH_START( msg )
00147
00148 RPC_DELEGATE( DHTPut, handlePutRequest );
00149 RPC_DELEGATE( CBRDHTGet, handleGetRequest );
00150 RPC_DELEGATE( DHTputCAPI, handlePutCAPIRequest );
00151 RPC_DELEGATE( DHTgetCAPI, handleGetCAPIRequest );
00152 RPC_DELEGATE( DHTdump, handleDumpDhtRequest );
00153 RPC_SWITCH_END( )
00154
00155 return RPC_HANDLED;
00156 }
00157
00158 void CBRDHT::handleRpcResponse(BaseResponseMessage* msg, cPolymorphic* context,
00159 int rpcId, simtime_t rtt)
00160 {
00161 RPC_SWITCH_START(msg)
00162 RPC_ON_RESPONSE(DHTPut){
00163 handlePutResponse(_DHTPutResponse, rpcId);
00164 EV << "[DHT::handleRpcResponse()]\n"
00165 << " DHT Put RPC Response received: id=" << rpcId
00166 << " msg=" << *_DHTPutResponse << " rtt=" << rtt
00167 << endl;
00168 break;
00169 }
00170 RPC_ON_RESPONSE(CBRDHTGet) {
00171 handleGetResponse(_CBRDHTGetResponse, rpcId);
00172 EV << "[DHT::handleRpcResponse()]\n"
00173 << " DHT Get RPC Response received: id=" << rpcId
00174 << " msg=" << *_CBRDHTGetResponse << " rtt=" << rtt
00175 << endl;
00176 break;
00177 }
00178 RPC_ON_RESPONSE(Lookup) {
00179 handleLookupResponse(_LookupResponse);
00180 EV << "[DHT::handleRpcResponse()]\n"
00181 << " Replica Set RPC Response received: id=" << rpcId
00182 << " msg=" << *_LookupResponse << " rtt=" << rtt
00183 << endl;
00184 break;
00185 }
00186 RPC_SWITCH_END()
00187 }
00188
00189 void CBRDHT::handleRpcTimeout(BaseCallMessage* msg, const TransportAddress& dest,
00190 cPolymorphic* context, int rpcId,
00191 const OverlayKey& destKey)
00192 {
00193 RPC_SWITCH_START(msg)
00194 RPC_ON_CALL(DHTPut){
00195 EV << "[DHT::handleRpcResponse()]\n"
00196 << " DHTPut Timeout"
00197 << endl;
00198
00199 std::map<int, PutMapEntry>::iterator it2 =
00200 putMap.find(rpcId);
00201
00202 if (it2 == putMap.end())
00203 return;
00204
00205 it2->second.numFailed++;
00206
00207 if (it2->second.numFailed / (double)it2->second.numSent >= 0.5) {
00208 DHTputCAPIResponse* capiPutRespMsg = new DHTputCAPIResponse();
00209 capiPutRespMsg->setKey(_DHTPutCall->getKey());
00210 capiPutRespMsg->setIsSuccess(false);
00211 sendRpcResponse(it2->second.callMsg, capiPutRespMsg);
00212 it2->second.callMsg = NULL;
00213 putMap.erase(rpcId);
00214 }
00215 break;
00216 }
00217 RPC_ON_CALL(CBRDHTGet) {
00218 EV << "[DHT::handleRpcResponse()]\n"
00219 << " DHTGet Timeout"
00220 << endl;
00221
00222 std::map<int, GetMapEntry>::iterator it2 =
00223 getMap.find(rpcId);
00224
00225 if (it2 == getMap.end())
00226 return;
00227
00228 if (it2->second.replica.size() > 0) {
00229
00230 NodeHandle fallbackReplica = it2->second.replica.back();
00231 CBRDHTGetCall* dhtRecall = new CBRDHTGetCall();
00232 dhtRecall->setOriginalKey(_CBRDHTGetCall->getOriginalKey());
00233 dhtRecall->setKey(_CBRDHTGetCall->getKey());
00234 dhtRecall->setIsHash(false);
00235 dhtRecall->setBitLength(GETCALL_L(dhtRecall));
00236 RECORD_STATS(normalMessages++;
00237 numBytesNormal += dhtRecall->getByteLength());
00238 sendRouteRpcCall(TIER1_COMP, fallbackReplica, dhtRecall,
00239 NULL, DEFAULT_ROUTING, -1, 0,
00240 it2->second.callMsg->getNonce());
00241 it2->second.numSent++;
00242 it2->second.replica.pop_back();
00243 return;
00244 } else if (it2->second.teamNumber < (numReplicaTeams - 1)) {
00245
00246 it2->second.teamNumber++;
00247 handleGetCAPIRequest(it2->second.callMsg, it2->second.teamNumber);
00248 return;
00249 } else {
00250
00251 DHTgetCAPIResponse* capiGetRespMsg = new DHTgetCAPIResponse();
00252
00253
00254 DhtDumpEntry result;
00255 result.setKey(_CBRDHTGetCall->getKey());
00256 result.setValue(BinaryValue::UNSPECIFIED_VALUE);
00257 capiGetRespMsg->setResultArraySize(1);
00258 capiGetRespMsg->setResult(0, result);
00259 capiGetRespMsg->setIsSuccess(false);
00260 sendRpcResponse(it2->second.callMsg, capiGetRespMsg);
00261 getMap.erase(rpcId);
00262 }
00263 break;
00264 }
00265 RPC_SWITCH_END( )
00266 }
00267
00268 void CBRDHT::handleUpperMessage(cMessage* msg)
00269 {
00270 error("DHT::handleUpperMessage(): Received message with unknown type!");
00271
00272 delete msg;
00273 }
00274
00275 void CBRDHT::handlePutRequest(DHTPutCall* dhtMsg)
00276 {
00277 std::string tempString = "PUT_REQUEST received: "
00278 + std::string(dhtMsg->getKey().toString(16));
00279 getParentModule()->getParentModule()->bubble(tempString.c_str());
00280
00281 if (!(dataStorage->isModifiable(dhtMsg->getKey(), dhtMsg->getKind(),
00282 dhtMsg->getId()))) {
00283
00284 NodeHandle sourceNode = dataStorage->getSourceNode(dhtMsg->getKey(),
00285 dhtMsg->getKind(), dhtMsg->getId());
00286 if (((!sourceNode.isUnspecified())
00287 && (!dhtMsg->getSrcNode().isUnspecified()) && (sourceNode
00288 != dhtMsg->getSrcNode())) || ((dhtMsg->getMaintenance())
00289 && (dhtMsg->getOwnerNode() == sourceNode))) {
00290
00291 DHTPutResponse* responseMsg = new DHTPutResponse();
00292 responseMsg->setKey(dhtMsg->getKey());
00293 tempString = "Error, not allowed to modify this key";
00294 responseMsg->setValue(BinaryValue(tempString));
00295 responseMsg->setBitLength(PUTRESPONSE_L(responseMsg));
00296 RECORD_STATS(normalMessages++;
00297 numBytesNormal += responseMsg->getByteLength());
00298 sendRpcResponse(dhtMsg, responseMsg);
00299 return;
00300 }
00301
00302 }
00303
00304
00305
00306
00307 dataStorage->removeData(dhtMsg->getKey(), dhtMsg->getKind(),
00308 dhtMsg->getId());
00309 if (dhtMsg->getValue().size() > 0) {
00310
00311 DHTTtlTimer *timerMsg = new DHTTtlTimer("ttl_timer");
00312 timerMsg->setKey(dhtMsg->getKey());
00313 scheduleAt(simTime() + dhtMsg->getTtl(), timerMsg);
00314
00315 bool err;
00316 dataStorage->addData(dhtMsg->getKey(), dhtMsg->getKind(),
00317 dhtMsg->getId(), dhtMsg->getValue(), timerMsg,
00318 dhtMsg->getIsModifiable(), dhtMsg->getSrcNode(),
00319 overlay->isSiblingFor(overlay->getThisNode(),
00320 dhtMsg->getKey(),
00321 1, &err));
00322 }
00323
00324
00325 DHTPutResponse* responseMsg = new DHTPutResponse();
00326 responseMsg->setKey(dhtMsg->getKey());
00327
00328 responseMsg->setValue(dhtMsg->getValue());
00329 responseMsg->setBitLength(PUTRESPONSE_L(responseMsg));
00330 RECORD_STATS(normalMessages++; numBytesNormal += responseMsg->getByteLength());
00331
00332 sendRpcResponse(dhtMsg, responseMsg);
00333 }
00334
00335 void CBRDHT::handleGetRequest(CBRDHTGetCall* dhtMsg)
00336 {
00337 std::string tempString = "GET_REQUEST received: "
00338 + std::string(dhtMsg->getKey().toString(16));
00339
00340 getParentModule()->getParentModule()->bubble(tempString.c_str());
00341
00342 BinaryValue storedValue;
00343 DhtDataEntry* dataEntry = dataStorage->getDataEntry(dhtMsg->getKey(), 1, 1);
00344 if (dataEntry) {
00345 storedValue = dataStorage->getDataEntry(dhtMsg->getKey(), 1, 1)->value;
00346 } else {
00347 storedValue = BinaryValue::UNSPECIFIED_VALUE;
00348 }
00349
00350
00351 CBRDHTGetResponse* responseMsg = new CBRDHTGetResponse();
00352
00353 responseMsg->setKey(dhtMsg->getKey());
00354 responseMsg->setOriginalKey(dhtMsg->getOriginalKey());
00355 responseMsg->setIsHash(false);
00356 if (storedValue.isUnspecified()) {
00357
00358 DhtDumpEntry result;
00359 result.setKey(dhtMsg->getKey());
00360 result.setValue(BinaryValue::UNSPECIFIED_VALUE);
00361 responseMsg->setResultArraySize(1);
00362 responseMsg->setResult(0, result);
00363 } else {
00364
00365 DhtDumpEntry result;
00366 result.setKey(dhtMsg->getKey());
00367 result.setValue(storedValue);
00368 responseMsg->setResultArraySize(1);
00369 responseMsg->setResult(0, result);
00370 }
00371 rpcIdMap.insert(make_pair(dhtMsg->getNonce(), (BaseCallMessage*)NULL));
00372
00373 responseMsg->setBitLength(GETRESPONSE_L(responseMsg));
00374 RECORD_STATS(normalMessages++;
00375 numBytesNormal += responseMsg->getByteLength());
00376 sendRpcResponse(dhtMsg, responseMsg);
00377 }
00378
00379 void CBRDHT::handlePutCAPIRequest(DHTputCAPICall* capiPutMsg)
00380 {
00381
00382 for (int i = 1; i < numReplicaTeams; i++) {
00383 DHTPutCall* teamCopyPutMsg = new DHTPutCall;
00384
00385
00386 teamCopyPutMsg->setValue(capiPutMsg->getValue());
00387 teamCopyPutMsg->setTtl(capiPutMsg->getTtl());
00388 teamCopyPutMsg->setIsModifiable(capiPutMsg->getIsModifiable());
00389 teamCopyPutMsg->setKind(capiPutMsg->getKind());
00390 teamCopyPutMsg->setId(capiPutMsg->getId());
00391
00392
00393 OverlayCtrlInfo controlInfo = *(check_and_cast<OverlayCtrlInfo*>(capiPutMsg->getControlInfo()));
00394 OverlayCtrlInfo* controlInfoCopy = new OverlayCtrlInfo;
00395 *controlInfoCopy = controlInfo;
00396 teamCopyPutMsg->setControlInfo(controlInfoCopy);
00397
00398
00399 OverlayKey destKey = capiPutMsg->getKey();
00400 for (int j = 0; j < i; j++) {
00401 destKey = OverlayKey::sha1(BinaryValue(destKey.toString(16).c_str()));
00402 }
00403 teamCopyPutMsg->setKey(destKey);
00404
00405
00406 LookupCall* replicaMsg = new LookupCall();
00407 replicaMsg->setKey(teamCopyPutMsg->getKey());
00408 replicaMsg->setNumSiblings(floor(numReplica / numReplicaTeams));
00409 int nonce = sendInternalRpcCall(OVERLAY_COMP, replicaMsg);
00410 rpcIdMap.insert(make_pair(nonce, teamCopyPutMsg));
00411 }
00412
00413
00414 LookupCall* replicaMsg = new LookupCall();
00415 replicaMsg->setKey(capiPutMsg->getKey());
00416 replicaMsg->setNumSiblings(floor(numReplica / numReplicaTeams));
00417 int nonce = sendInternalRpcCall(OVERLAY_COMP, replicaMsg);
00418 rpcIdMap.insert(make_pair(nonce, capiPutMsg));
00419 }
00420
00421 void CBRDHT::handleGetCAPIRequest(DHTgetCAPICall* capiGetMsg, int teamnum) {
00422
00423 if (teamnum >= numReplicaTeams)
00424 return;
00425
00426 OverlayKey originalKey = capiGetMsg->getKey();
00427 std::vector<OverlayKey> possibleKeys;
00428
00429 assert(!originalKey.isUnspecified());
00430 possibleKeys.push_back(originalKey);
00431
00432 for (int i = 1; i < numReplicaTeams; i++) {
00433
00434 OverlayKey keyHash = originalKey;
00435 for (int j = 0; j < i; j++) {
00436 keyHash = OverlayKey::sha1(BinaryValue(keyHash.toString(16).c_str()));
00437 }
00438 assert(!keyHash.isUnspecified());
00439 possibleKeys.push_back(keyHash);
00440 }
00441
00442
00443 std::vector<OverlayKey> orderedKeys;
00444 OverlayKey compareKey = overlay->getThisNode().getKey();
00445
00446 while (possibleKeys.size() > 0) {
00447 OverlayKey bestKey = possibleKeys[0];
00448 int bestpos = 0;
00449
00450
00451 for (uint i = 0; i < possibleKeys.size(); i++) {
00452
00453 if (coordBasedRouting
00454 ->getEuclidianDistanceByKeyAndCoords(possibleKeys[i],
00455 neighborCache->getNpsAccess().getOwnCoordinates(),
00456 overlay->getBitsPerDigit()) <
00457 coordBasedRouting
00458 ->getEuclidianDistanceByKeyAndCoords(bestKey,
00459 neighborCache->getNpsAccess().getOwnCoordinates(),
00460 overlay->getBitsPerDigit())) {
00461 bestKey = possibleKeys[i];
00462 bestpos = i;
00463 }
00464 }
00465
00466 orderedKeys.push_back(bestKey);
00467 possibleKeys.erase(possibleKeys.begin()+bestpos);
00468 }
00469
00470
00471
00472
00473
00474
00475
00476
00477
00478 OverlayKey searchKey = orderedKeys[teamnum];
00479
00480 #define DIRECT_ROUTE_GET
00481 #ifndef DIRECT_ROUTE_GET
00482
00483 LookupCall* replicaMsg = new LookupCall();
00484 replicaMsg->setKey(searchKey);
00485 replicaMsg->setNumSiblings(floor(numReplica / numReplicaTeams));
00486 int nonce = sendInternalRpcCall(OVERLAY_COMP, replicaMsg);
00487 rpcIdMap.insert(make_pair(nonce, capiGetMsg));
00488 lastGetCall = SIMTIME_DBL(simTime());
00489
00490 #else
00491
00492 GetMapEntry mapEntry;
00493 mapEntry.numSent = 0;
00494
00495
00496 std::map<int, GetMapEntry>::iterator it2 =
00497 getMap.find(capiGetMsg->getNonce());
00498
00499 if (it2 != getMap.end()) {
00500 mapEntry = it2->second;
00501 } else {
00502 mapEntry.teamNumber = 0;
00503 }
00504 mapEntry.numAvailableReplica = 1;
00505 mapEntry.numResponses = 0;
00506 mapEntry.callMsg = capiGetMsg;
00507 mapEntry.hashVector = NULL;
00508 mapEntry.replica.clear();
00509 for (unsigned int i = 0; i < 1; i++) {
00510
00511 if (i == 0) {
00512 CBRDHTGetCall* dhtMsg = new CBRDHTGetCall();
00513
00514 dhtMsg->setOriginalKey(capiGetMsg->getKey());
00515 dhtMsg->setKey(searchKey);
00516
00517 dhtMsg->setIsHash(false);
00518 dhtMsg->setKind(capiGetMsg->getKind());
00519 dhtMsg->setId(capiGetMsg->getId());
00520 dhtMsg->setBitLength(GETCALL_L(dhtMsg));
00521 RECORD_STATS(normalMessages++;
00522 numBytesNormal += dhtMsg->getByteLength());
00523
00524 sendRouteRpcCall(TIER1_COMP, searchKey, dhtMsg,
00525 NULL, DEFAULT_ROUTING, -1, 0,
00526 capiGetMsg->getNonce());
00527
00528
00529
00530
00531
00532 mapEntry.numSent++;
00533 } else {
00534
00535
00536 }
00537 }
00538
00539
00540
00541
00542
00543
00544
00545 if (it2 != getMap.end())
00546 getMap.erase(it2);
00547 getMap.insert(make_pair(capiGetMsg->getNonce(), mapEntry));
00548 #endif
00549 }
00550
00551 void CBRDHT::handleDumpDhtRequest(DHTdumpCall* call)
00552 {
00553 DHTdumpResponse* response = new DHTdumpResponse();
00554 DhtDumpVector* dumpVector = dataStorage->dumpDht();
00555
00556 response->setRecordArraySize(dumpVector->size());
00557
00558 for (uint i = 0; i < dumpVector->size(); i++) {
00559 response->setRecord(i, (*dumpVector)[i]);
00560 }
00561
00562 delete dumpVector;
00563
00564 sendRpcResponse(call, response);
00565 }
00566
00567 void CBRDHT::handlePutResponse(DHTPutResponse* dhtMsg, int rpcId)
00568 {
00569 std::map<int, PutMapEntry>::iterator it2 =
00570 putMap.find(rpcId);
00571
00572 if (it2 == putMap.end())
00573 return;
00574
00575 it2->second.numResponses++;
00576
00577 if (it2->second.numResponses / (double)it2->second.numSent > 0.5) {
00578 DHTputCAPIResponse* capiPutRespMsg = new DHTputCAPIResponse();
00579 capiPutRespMsg->setKey(dhtMsg->getKey());
00580 capiPutRespMsg->setValue(dhtMsg->getValue());
00581 capiPutRespMsg->setIsSuccess(true);
00582 sendRpcResponse(it2->second.callMsg, capiPutRespMsg);
00583 it2->second.callMsg = NULL;
00584 putMap.erase(rpcId);
00585 }
00586 }
00587
00588 void CBRDHT::handleGetResponse(CBRDHTGetResponse* dhtMsg, int rpcId)
00589 {
00590 std::map<unsigned int, BaseCallMessage*>::iterator it =
00591 rpcIdMap.find(dhtMsg->getNonce());
00592 std::map<int, GetMapEntry>::iterator it2 =
00593 getMap.find(rpcId);
00594
00595
00596 if (it2 == getMap.end()) {
00597 std::cout << "- 1 -" << std::endl;
00598 return;
00599 }
00600
00601 if (!dhtMsg->getIsHash()) {
00602
00603
00604
00605 if (dhtMsg->getHashValue().size() > 0 || dhtMsg->getResultArraySize() > 0) {
00606
00607 DHTgetCAPIResponse* capiGetRespMsg = new DHTgetCAPIResponse();
00608
00609
00610 DhtDumpEntry result;
00611 result.setKey(dhtMsg->getKey());
00612 result.setValue(dhtMsg->getResult(0).getValue());
00613 capiGetRespMsg->setResultArraySize(1);
00614 capiGetRespMsg->setResult(0, result);
00615
00616
00617
00618 capiGetRespMsg->setIsSuccess(true);
00619 sendRpcResponse(it2->second.callMsg, capiGetRespMsg);
00620 getMap.erase(rpcId);
00621 return;
00622 } else if (it2->second.replica.size() > 0) {
00623
00624 NodeHandle fallbackReplica = it2->second.replica.back();
00625
00626 std::cout << "[" << overlay->getThisNode().getAddress() << "] " << "Empty value received. Asking replica now ("<< it2->second.replica.size()<<" left)!" << std::endl;
00627
00628 CBRDHTGetCall* dhtRecall = new CBRDHTGetCall();
00629 dhtRecall->setOriginalKey(dhtMsg->getOriginalKey());
00630 dhtRecall->setKey(dhtMsg->getKey());
00631 dhtRecall->setIsHash(false);
00632 dhtRecall->setBitLength(GETCALL_L(dhtRecall));
00633 RECORD_STATS(normalMessages++;
00634 numBytesNormal += dhtRecall->getByteLength());
00635 sendRouteRpcCall(TIER1_COMP, fallbackReplica, dhtRecall,
00636 NULL, DEFAULT_ROUTING, -1, 0,
00637 it2->second.callMsg->getNonce());
00638 it2->second.numSent++;
00639 it2->second.replica.pop_back();
00640 return;
00641 } else if (it2->second.teamNumber < (numReplicaTeams - 1)) {
00642
00643
00644 std::cout << "it2->second.teamNumber (" << it2->second.teamNumber << ") < (numReplicaTeams - 1) (" << (numReplicaTeams - 1) << ")" << std::endl;
00645 std::cout << "[" << overlay->getThisNode().getAddress() << "] " << "No more fallback replica in this team "<< it2->second.teamNumber<<". Trying next one ("<< it2->second.teamNumber+1 << ")..." << std::endl;
00646
00647 it2->second.teamNumber++;
00648 handleGetCAPIRequest(it2->second.callMsg, it2->second.teamNumber);
00649 return;
00650 } else {
00651
00652
00653 std::cout << "[" << overlay->getThisNode().getAddress() << "] " << "No more fallback replica. Lookup failed. :(" << std::endl;
00654
00655 DHTgetCAPIResponse* capiGetRespMsg = new DHTgetCAPIResponse();
00656
00657
00658 DhtDumpEntry result;
00659 result.setKey(dhtMsg->getKey());
00660 result.setValue(BinaryValue::UNSPECIFIED_VALUE);
00661 capiGetRespMsg->setResultArraySize(1);
00662 capiGetRespMsg->setResult(0, result);
00663 capiGetRespMsg->setIsSuccess(false);
00664 sendRpcResponse(it2->second.callMsg, capiGetRespMsg);
00665 getMap.erase(rpcId);
00666 }
00667 }
00668 }
00669
00670 void CBRDHT::update(const NodeHandle& node, bool joined)
00671 {
00672 OverlayKey key;
00673 DHTPutCall* dhtMsg;
00674 bool err = false;
00675
00676 DhtDataEntry entry;
00677
00678 DhtDataMap::iterator it = dataStorage->begin();
00679 for (unsigned int i = 0; i < dataStorage->getSize(); i++) {
00680 key = it->first;
00681 entry = it->second;
00682 if (joined) {
00683 if (entry.responsible && (overlay->isSiblingFor(node, key,
00684 numReplica, &err)
00685 || err)) {
00686
00687 dhtMsg = new DHTPutCall();
00688 dhtMsg->setKey(key);
00689 dhtMsg->setValue(entry.value);
00690 dhtMsg->setKind(entry.kind);
00691 dhtMsg->setId(entry.id);
00692
00693
00694
00695 dhtMsg->setTtl((int)SIMTIME_DBL(entry.ttlMessage->getArrivalTime()
00696 - simTime()));
00697 dhtMsg->setIsModifiable(entry.is_modifiable);
00698 dhtMsg->setMaintenance(true);
00699 dhtMsg->setBitLength(PUTCALL_L(dhtMsg));
00700 RECORD_STATS(maintenanceMessages++;
00701 numBytesMaintenance += dhtMsg->getByteLength());
00702 sendRouteRpcCall(TIER1_COMP, node, dhtMsg);
00703 }
00704
00705 if (err) {
00706 EV << "[DHT::update()]\n"
00707 << " Unable to know if key: " << key
00708 << " is in range of node: " << node
00709 << endl;
00710 }
00711 } else {
00712 #if 0
00713
00714
00715 LookupCall* replicaMsg = new LookupCall();
00716 replicaMsg->setKey(key);
00717 replicaMsg->setNumSiblings(numReplica);
00718 int nonce = sendInternalRpcCall(OVERLAY_COMP,
00719 replicaMsg);
00720 dhtMsg = new DHTPutCall();
00721 dhtMsg->setKey(key);
00722 dhtMsg->setValue(entry.value);
00723 dhtMsg->setTtl((int)(entry.ttlMessage->arrivalTime()
00724 - simulation.simTime()));
00725 dhtMsg->setIsModifiable(entry.is_modifiable);
00726 dhtMsg->setMaintenance(true);
00727 dhtMsg->setLength(PUTCALL_L(dhtMsg));
00728
00729 rpcIdMap.insert(make_pair(nonce, dhtMsg));
00730 #endif
00731 }
00732
00733 entry.responsible = overlay->isSiblingFor(overlay->getThisNode(),
00734 key, 1, &err);
00735 it++;
00736 }
00737 }
00738
00739 void CBRDHT::handleLookupResponse(LookupResponse* lookupMsg)
00740 {
00741 std::map<unsigned int, BaseCallMessage*>::iterator it =
00742 rpcIdMap.find(lookupMsg->getNonce());
00743
00744 if (it == rpcIdMap.end() || it->second == NULL)
00745 return;
00746
00747 if (dynamic_cast<DHTputCAPICall*> (it->second)) {
00748
00749 #if 0
00750 cout << "DHT::handleLookupResponse(): PUT "
00751 << lookupMsg->getKey() << " ("
00752 << overlay->getThisNode().getKey() << ")" << endl;
00753
00754 for (unsigned int i = 0; i < lookupMsg->getSiblingsArraySize(); i++) {
00755 cout << i << ": " << lookupMsg->getSiblings(i) << endl;
00756 }
00757 #endif
00758
00759 DHTputCAPICall* capiPutMsg = dynamic_cast<DHTputCAPICall*> (it->second);
00760 rpcIdMap.erase(lookupMsg->getNonce());
00761
00762
00763 if ((lookupMsg->getIsValid() == false)
00764 || (lookupMsg->getSiblingsArraySize() == 0)) {
00765
00766 EV << "[DHT::handleLookupResponse()]\n"
00767 << " Unable to get replica list : invalid lookup"
00768 << endl;
00769 DHTputCAPIResponse* capiPutRespMsg = new DHTputCAPIResponse();
00770 capiPutRespMsg->setKey(lookupMsg->getKey());
00771 capiPutRespMsg->setIsSuccess(false);
00772 sendRpcResponse(capiPutMsg, capiPutRespMsg);
00773 return;
00774 }
00775
00776 for (unsigned int i = 0; i < lookupMsg->getSiblingsArraySize(); i++) {
00777 DHTPutCall* dhtMsg = new DHTPutCall();
00778 dhtMsg->setKey(capiPutMsg->getKey());
00779 dhtMsg->setValue(capiPutMsg->getValue());
00780 dhtMsg->setKind(capiPutMsg->getKind());
00781 dhtMsg->setId(capiPutMsg->getId());
00782 dhtMsg->setTtl(capiPutMsg->getTtl());
00783 dhtMsg->setIsModifiable(capiPutMsg->getIsModifiable());
00784 dhtMsg->setMaintenance(false);
00785 dhtMsg->setBitLength(PUTCALL_L(dhtMsg));
00786 RECORD_STATS(normalMessages++;
00787 numBytesNormal += dhtMsg->getByteLength());
00788 sendRouteRpcCall(TIER1_COMP, lookupMsg->getSiblings(i),
00789 dhtMsg, NULL, DEFAULT_ROUTING, -1,
00790 0, capiPutMsg->getNonce());
00791 }
00792
00793 PutMapEntry mapEntry;
00794 mapEntry.callMsg = capiPutMsg;
00795 mapEntry.numResponses = 0;
00796 mapEntry.numFailed = 0;
00797 mapEntry.numSent = lookupMsg->getSiblingsArraySize();
00798
00799 putMap.insert(make_pair(capiPutMsg->getNonce(), mapEntry));
00800 }
00801 else if (dynamic_cast<DHTgetCAPICall*>(it->second)) {
00802
00803 #if 0
00804 cout << "DHT::handleLookupResponse(): GET "
00805 << lookupMsg->getKey() << " ("
00806 << overlay->getThisNode().getKey() << ")" << endl;
00807
00808 for (unsigned int i = 0; i < lookupMsg->getSiblingsArraySize(); i++) {
00809 cout << i << ": " << lookupMsg->getSiblings(i) << endl;
00810 }
00811 #endif
00812
00813 DHTgetCAPICall* capiGetMsg = dynamic_cast<DHTgetCAPICall*>(it->second);
00814 rpcIdMap.erase(lookupMsg->getNonce());
00815
00816
00817 if ((lookupMsg->getIsValid() == false)
00818 || (lookupMsg->getSiblingsArraySize() == 0)) {
00819
00820 EV << "[DHT::handleLookupResponse()]\n"
00821 << " Unable to get replica list : invalid lookup"
00822 << endl;
00823 DHTgetCAPIResponse* capiGetRespMsg = new DHTgetCAPIResponse();
00824
00825
00826 DhtDumpEntry result;
00827 result.setKey(lookupMsg->getKey());
00828 result.setValue(BinaryValue::UNSPECIFIED_VALUE);
00829 capiGetRespMsg->setResultArraySize(1);
00830 capiGetRespMsg->setResult(0, result);
00831 capiGetRespMsg->setIsSuccess(false);
00832 sendRpcResponse(capiGetMsg, capiGetRespMsg);
00833 return;
00834 }
00835
00836
00837 GetMapEntry mapEntry;
00838 mapEntry.numSent = 0;
00839
00840
00841
00842 std::map<int, GetMapEntry>::iterator it2 =
00843 getMap.find(capiGetMsg->getNonce());
00844
00845 if (it2 != getMap.end()) {
00846 mapEntry = it2->second;
00847 } else {
00848 mapEntry.teamNumber = 0;
00849 }
00850 mapEntry.numAvailableReplica = lookupMsg->getSiblingsArraySize();
00851 mapEntry.numResponses = 0;
00852 mapEntry.callMsg = capiGetMsg;
00853 mapEntry.hashVector = NULL;
00854 mapEntry.replica.clear();
00855 for (unsigned int i = 0; i < lookupMsg->getSiblingsArraySize(); i++) {
00856
00857 if (i == 0) {
00858 CBRDHTGetCall* dhtMsg = new CBRDHTGetCall();
00859
00860 dhtMsg->setOriginalKey(capiGetMsg->getKey());
00861 dhtMsg->setKey(lookupMsg->getKey());
00862
00863 dhtMsg->setIsHash(false);
00864 dhtMsg->setKind(capiGetMsg->getKind());
00865 dhtMsg->setId(capiGetMsg->getId());
00866 dhtMsg->setBitLength(GETCALL_L(dhtMsg));
00867 RECORD_STATS(normalMessages++;
00868 numBytesNormal += dhtMsg->getByteLength());
00869 sendRouteRpcCall(TIER1_COMP, lookupMsg->getSiblings(i), dhtMsg,
00870 NULL, DEFAULT_ROUTING, -1, 0,
00871 capiGetMsg->getNonce());
00872 mapEntry.numSent++;
00873 } else {
00874
00875 mapEntry.replica.push_back(lookupMsg->getSiblings(i));
00876 }
00877 }
00878
00879
00880
00881
00882
00883
00884
00885 if (it2 != getMap.end())
00886 getMap.erase(it2);
00887 getMap.insert(make_pair(capiGetMsg->getNonce(), mapEntry));
00888 } else if (dynamic_cast<DHTPutCall*>(it->second)) {
00889 DHTPutCall* putMsg = dynamic_cast<DHTPutCall*>(it->second);
00890 rpcIdMap.erase(lookupMsg->getNonce());
00891
00892 if ((lookupMsg->getIsValid() == false)
00893 || (lookupMsg->getSiblingsArraySize() == 0)) {
00894
00895 EV << "[DHT::handleLookupResponse()]\n"
00896 << " Unable to get replica list : invalid lookup"
00897 << endl;
00898 delete putMsg;
00899 return;
00900 }
00901
00902 for( unsigned int i = 0; i < lookupMsg->getSiblingsArraySize(); i++ ) {
00903 RECORD_STATS(maintenanceMessages++;
00904 numBytesMaintenance += putMsg->getByteLength());
00905
00906 sendRouteRpcCall(TIER1_COMP, lookupMsg->getSiblings(i),
00907 new DHTPutCall(*putMsg));
00908 }
00909
00910 delete putMsg;
00911 }
00912 }
00913
00914 void CBRDHT::finishApp()
00915 {
00916 simtime_t time = globalStatistics->calcMeasuredLifetime(creationTime);
00917
00918 if (time != 0) {
00919
00920 globalStatistics->addStdDev("DHT: Sent Maintenance Messages/s",
00921 maintenanceMessages / time);
00922 globalStatistics->addStdDev("DHT: Sent Normal Messages/s",
00923 normalMessages / time);
00924 globalStatistics->addStdDev("DHT: Sent Maintenance Bytes/s",
00925 numBytesMaintenance / time);
00926 globalStatistics->addStdDev("DHT: Sent Normal Bytes/s",
00927 numBytesNormal / time);
00928 }
00929 }
00930
00931 int CBRDHT::resultValuesBitLength(DHTGetResponse* msg) {
00932 int bitSize = 0;
00933 for (uint i = 0; i < msg->getResultArraySize(); i++) {
00934 bitSize += msg->getResult(i).getValue().size();
00935
00936 }
00937 return bitSize;
00938 }
00939