BaseRpc Class Reference

#include <BaseRpc.h>

Inheritance diagram for BaseRpc:

RpcListener BaseApp BaseOverlay DHT DHTTestApp DHTXMLRealworldApp GIASearchApp KBRTestApp RealWorldTestApp SimpleClient Broose Chord Gia Pastry Vast List of all members.

Detailed Description

Base class for RPCs.

Base class for RPCs.

Author:
Bernhard Heep (initial)

Sebastian Mies (rpc, lookup)

Gregoire Menuel (separation from BaseRpc)


Public Member Functions

 BaseRpc ()
uint32_t sendRpcMessage (const TransportAddress &dest, BaseCallMessage *msg, RpcListener *rpcListener=NULL, const OverlayKey &destKey=OverlayKey::UNSPECIFIED_KEY, int rpcId=-1, simtime_t timeout=-1, int retries=0)
 Sends a Remote-Procedure-Call message to the underlay.
uint32_t sendRpcMessage (int destType, const TransportAddress &dest, BaseCallMessage *msg, RpcListener *rpcListener=NULL, const OverlayKey &destKey=OverlayKey::UNSPECIFIED_KEY, int rpcId=-1, simtime_t timeout=-1, int retries=0)
 Sends a Remote-Procedure-Call message to the underlay.
void cancelRpcMessage (uint32_t nonce)
 Cancels a Remote-Procedure-Call.
void sendRpcResponse (int destType, BaseCallMessage *call, BaseResponseMessage *response)
 Send Remote-Procedure response message and deletes call message.
void sendRpcResponse (BaseCallMessage *call, BaseResponseMessage *response)

Protected Member Functions

virtual bool internalHandleRpc (BaseCallMessage *msg)
 Handles internal rpc requests.
void initRpcs ()
 Initializes Remote-Procedure state.
void finishRpcs ()
 Deinitializes Remote-Procedure state.
virtual void internalHandleRpcMessage (BaseRpcMessage *msg)
 Handles incoming rpc messages and delegates them to the corresponsing listeners or handlers.
virtual bool handleRpc (BaseCallMessage *msg)
 Processes Remote-Procedure-Call invokation messages.
virtual void sendRpcMessageToDestination (int destType, const TransportAddress &dest, const OverlayKey &destKey, BaseOverlayMessage *message)

Protected Attributes

NodeHandle thisNode
 Virtual destructor.
bool debugOutput
GlobalParametersglobalParameters

Private Types

typedef hash_map< int, RpcStateRpcStates

Private Attributes

int rpcsPending
RpcListenerdefaultRpcListener
RpcStates rpcStates
double rpcUdpTimeout
double rpcKeyTimeout

Classes

class  RpcState


Member Typedef Documentation

typedef hash_map<int,RpcState> BaseRpc::RpcStates [private]


Constructor & Destructor Documentation

BaseRpc::BaseRpc (  ) 

00053 {
00054     defaultRpcListener = NULL;
00055 }


Member Function Documentation

bool BaseRpc::internalHandleRpc ( BaseCallMessage *  msg  )  [protected, virtual]

Handles internal rpc requests.


This method is used to implement basic functionionality in the BaseRpc.

Parameters:
msg The call message
Returns:
bool true, if call has been handled.

Reimplemented in BaseOverlay.

00262 {
00263     return false;
00264 }

void BaseRpc::initRpcs (  )  [protected]

Initializes Remote-Procedure state.

00059 {
00060     globalParameters = GlobalParametersAccess().get();
00061         
00062     rpcsPending = 0;
00063     rpcStates.clear();
00064 
00065     defaultRpcListener = new RpcListener();
00066 }

void BaseRpc::finishRpcs (  )  [protected]

Deinitializes Remote-Procedure state.

00070 {
00071     // stop all rpcs
00072     for (RpcStates::iterator i = rpcStates.begin();
00073         i != rpcStates.end(); i++) {
00074         cancelAndDelete(i->second.callMsg);
00075         cancelAndDelete(i->second.timeoutMsg);
00076     }
00077     rpcStates.clear();
00078 
00079     // delete default rpc listener
00080     if (defaultRpcListener!=NULL) {
00081         delete defaultRpcListener;
00082         defaultRpcListener = NULL;
00083     }
00084 }

void BaseRpc::internalHandleRpcMessage ( BaseRpcMessage *  msg  )  [protected, virtual]

Handles incoming rpc messages and delegates them to the corresponsing listeners or handlers.

Parameters:
msg The message to handle.
00175 {
00176     // check if this is a rpc call message
00177     BaseCallMessage* rpCall = dynamic_cast<BaseCallMessage*>(msg);
00178     if (rpCall != NULL) {
00179         bool rpcHandled = true;
00180         if (!handleRpc(rpCall)) rpcHandled = internalHandleRpc(rpCall);
00181         if (!rpcHandled) {
00182             EV << "[BaseRpc::internalHandleRpcMessage() @ " << thisNode.ip
00183                << " (" << thisNode.key.toString(16) << ")]\n"
00184                << "    Error: RPC '" << msg->fullName()<< "' was not handled"
00185                << endl;
00186             delete msg;
00187         }
00188         return;
00189     }
00190 
00191     // get nonce
00192     int nonce = msg->getNonce();
00193 
00194     // nonce known? no -> delete message and return
00195     if (rpcStates.count(nonce)==0) {
00196         EV << "[BaseRpc::internalHandleRpcMessage() @ " << thisNode.ip
00197            << " " << thisNode.key.toString(16) << ")]\n"
00198            << "    RPC: Nonce Unknown"
00199            << endl;     
00200         delete msg;
00201         return;
00202     }
00203 
00204     // get state and remove from map
00205     RpcState state = rpcStates[nonce];
00206     rpcStates.erase(nonce);
00207 
00208     // is timeout message?
00209     if ( msg->isSelfMessage() && (dynamic_cast<RpcTimeoutMessage*>(msg) != NULL)) { // yes-> inform listener
00210 
00211         // retry?
00212         state.retries--;
00213         simtime_t timeout = simulation.simTime() - state.timeSent;
00214         if (state.retries>=0) {
00215             sendRpcMessageToDestination(state.destType, state.dest,
00216                                         state.destKey,
00217                                         dynamic_cast<BaseCallMessage*>
00218                                         (state.callMsg->dup()));
00219             if (timeout!=0)
00220                 scheduleAt( simulation.simTime() + timeout, msg );
00221             rpcStates[nonce] = state;
00222             return;
00223         }
00224 
00225         // inform listener
00226         if ( state.listener != NULL )
00227             state.listener->handleRpcTimeout( state.callMsg, state.dest,
00228                                               state.id, state.destKey );
00229 
00230         // inform overlay
00231         handleRpcTimeout( state.callMsg, state.dest, state.id, state.destKey );
00232 
00233     } else { // no-> handle rpc response
00234 
00235         // get parameters
00236         simtime_t rtt = simulation.simTime() - state.timeSent;
00237         BaseResponseMessage* response
00238         = dynamic_cast<BaseResponseMessage*>(msg);
00239 
00240         // inform listener
00241         if ( state.listener != NULL )
00242             state.listener->handleRpcResponse( response, state.id, rtt );
00243 
00244         // inform overlay
00245         handleRpcResponse( response, state.id, rtt );
00246 
00247         // delete response
00248         delete response;
00249     }
00250 
00251     // delete messages
00252     cancelAndDelete(state.callMsg);
00253     cancelAndDelete(state.timeoutMsg);
00254 
00255     // clean up pointers
00256     state.callMsg = NULL;
00257     state.timeoutMsg = NULL;
00258 }

uint32_t BaseRpc::sendRpcMessage ( const TransportAddress dest,
BaseCallMessage *  msg,
RpcListener rpcListener = NULL,
const OverlayKey destKey = OverlayKey::UNSPECIFIED_KEY,
int  rpcId = -1,
simtime_t  timeout = -1,
int  retries = 0 
)

Sends a Remote-Procedure-Call message to the underlay.


Compatibility function. See the other sendRpcMessage function for more information

Parameters:
dest Destination node handle
msg RPC Call Message
rpcListener RPC Listener
destKey first route the RPC to the node that is responsible for kestkey
rpcId RPC id
timeout RPC timeout
retries How often we try to resent rpc call, if it gets lost
Returns:
The nonce of the RPC
00093 {
00094     if (destKey.isUnspecified()) {
00095         return sendRpcMessage( RPC_TO_UDP, dest, msg, rpcListener, destKey, rpcId, timeout, retries );
00096     } else {
00097         // send message to key
00098         return sendRpcMessage( RPC_TO_KEY, dest, msg, rpcListener, destKey, rpcId, timeout, retries );
00099     }
00100 }  

uint32_t BaseRpc::sendRpcMessage ( int  destType,
const TransportAddress dest,
BaseCallMessage *  msg,
RpcListener rpcListener = NULL,
const OverlayKey destKey = OverlayKey::UNSPECIFIED_KEY,
int  rpcId = -1,
simtime_t  timeout = -1,
int  retries = 0 
)

Sends a Remote-Procedure-Call message to the underlay.


If no timeout is provided, a default value of globalParameters.rpcUdpTimeout for underlay and globalParameters.rpcKeyTimeout for a overlay rpc is used. After a timeout the message gets retransmitted for at maximum retries times.

The destKey attribute is kept untouched.

Parameters:
destType The type of destination (RPC_TO_UDP, RPC_TO_KEY, RPC_TO_LOWERTIER, RPC_TO_UPPERTIER)
dest Destination node handle
msg RPC Call Message
rpcListener RPC Listener
destKey first route the RPC to the node that is responsible for kestkey
rpcId RPC id
timeout RPC timeout
retries How often we try to resent rpc call, if it gets lost
Returns:
The nonce of the RPC
00109 {
00110 
00111     // create nonce, timeout and set default parameters
00112     uint nonce;
00113     do {
00114         nonce = intuniform( 0, 2147483647);
00115     } while (rpcStates.count(nonce) > 0);
00116 
00117 
00118     if (timeout == -1)
00119         timeout = destKey.isUnspecified() ?
00120             globalParameters->getRpcUdpTimeout() :
00121             globalParameters->getRpcKeyTimeout();
00122     if (rpcListener == NULL)
00123         rpcListener = defaultRpcListener;
00124 
00125     // create state
00126     RpcState state;
00127     state.id = rpcId;
00128     state.timeSent = simulation.simTime();
00129     state.dest = dest;
00130     state.destKey = destKey;
00131     state.listener = rpcListener;
00132     state.timeoutMsg = new RpcTimeoutMessage();
00133     state.timeoutMsg->setNonce(nonce);
00134     state.retries = retries;
00135     state.destType = destType;
00136 
00137 
00138 
00139     if (rpcStates.count(nonce) > 0)
00140         error("RPC nonce collision");
00141 
00142     // set message parameters
00143     msg->setNonce( nonce );
00144     msg->setSrcNode( thisNode );
00145     msg->setType(RPC);
00146 
00147     // save copy of call message in RpcState
00148     state.callMsg = dynamic_cast<BaseCallMessage*>(msg->dup());
00149 
00150     // register state
00151     rpcStates[nonce] = state;
00152 
00153     // schedule timeout message
00154     if (timeout!=0)
00155         scheduleAt( simulation.simTime() + timeout, state.timeoutMsg);
00156 
00157     sendRpcMessageToDestination(destType, dest, destKey, msg);
00158 
00159     return nonce;
00160 }

void BaseRpc::cancelRpcMessage ( uint32_t  nonce  ) 

Cancels a Remote-Procedure-Call.

Parameters:
nonce The nonce of the RPC
00164 {
00165     if (rpcStates.count(nonce)==0)
00166         return;
00167     RpcState state = rpcStates[nonce];
00168     rpcStates.erase(nonce);
00169     cancelAndDelete(state.callMsg);
00170     cancelAndDelete(state.timeoutMsg);
00171 }

void BaseRpc::sendRpcResponse ( int  destType,
BaseCallMessage *  call,
BaseResponseMessage *  response 
)

Send Remote-Procedure response message and deletes call message.


The destKey attribute is kept untouched. If call or reponse is NULL no reponse will be sent.

Parameters:
destType the destination type of the RPC
call The corresponding call message to the reponse
response The call return value
00274 {
00275     if (call==NULL || response==NULL) {
00276         if ( call!=NULL )
00277             delete call;
00278         return;
00279     }
00280     response->setSrcNode( thisNode );
00281     response->setType( RPC );
00282     response->setNonce( call->getNonce() );
00283     sendRpcMessageToDestination(destType, call->getSrcNode(), call->getSrcNode().getKey(), response );
00284     delete call;
00285 
00286 }

void BaseRpc::sendRpcResponse ( BaseCallMessage *  call,
BaseResponseMessage *  response 
)

00292 {
00293     sendRpcResponse(RPC_TO_UDP, call, response);
00294 }

bool BaseRpc::handleRpc ( BaseCallMessage *  msg  )  [protected, virtual]

Processes Remote-Procedure-Call invokation messages.


This method should be overloaded when the overlay provides RPC functionality.

Returns:
true, if rpc has been handled

Reimplemented in DHT, Broose, Chord, and Koorde.

00268 {
00269     return false;
00270 }

void BaseRpc::sendRpcMessageToDestination ( int  destType,
const TransportAddress dest,
const OverlayKey destKey,
BaseOverlayMessage *  message 
) [protected, virtual]

Reimplemented in BaseApp, and BaseOverlay.

00301 {
00302     switch(destType) {
00303       case RPC_TO_UDP:
00304           opp_error( "sendRpcMessageToDestination with UDP: Not implemented!" );
00305           delete message;
00306           break;
00307       case RPC_TO_KEY:
00308           opp_error( "sendRpcMessageToDestination with KEY: Not implemented!" );
00309           delete message;
00310           break;
00311       case RPC_TO_UPPERTIER:
00312           send( message, "to_upperTier");
00313           break;
00314       case RPC_TO_LOWERTIER:
00315           send( message, "to_lowerTier");
00316           break;
00317     }
00318 }


Member Data Documentation

NodeHandle BaseRpc::thisNode [protected]

Virtual destructor.

Reimplemented in Gia.

bool BaseRpc::debugOutput [protected]

Reimplemented in BaseApp, BaseOverlay, and DHTTestApp.

GlobalParameters* BaseRpc::globalParameters [protected]

int BaseRpc::rpcsPending [private]

RpcListener* BaseRpc::defaultRpcListener [private]

RpcStates BaseRpc::rpcStates [private]

double BaseRpc::rpcUdpTimeout [private]

double BaseRpc::rpcKeyTimeout [private]


The documentation for this class was generated from the following files:
Generated on Wed Sep 26 12:13:01 2007 for ITM OverSim by  doxygen 1.5.1