From 0ea5fc66924303d1bf73ba283a383e2aadee02f2 Mon Sep 17 00:00:00 2001 From: neodarz Date: Sat, 11 Aug 2018 20:21:34 +0200 Subject: Initial commit --- docs/doxygen/nel/naming__client_8cpp-source.html | 625 +++++++++++++++++++++++ 1 file changed, 625 insertions(+) create mode 100644 docs/doxygen/nel/naming__client_8cpp-source.html (limited to 'docs/doxygen/nel/naming__client_8cpp-source.html') diff --git a/docs/doxygen/nel/naming__client_8cpp-source.html b/docs/doxygen/nel/naming__client_8cpp-source.html new file mode 100644 index 00000000..48527f42 --- /dev/null +++ b/docs/doxygen/nel/naming__client_8cpp-source.html @@ -0,0 +1,625 @@ + + + + nevrax.org : docs + + + + + + + + + + + + + + +
# Home   # nevrax.com   
+ + + + +
Nevrax
+ + + + + + + + + + +
+ + +
+ Nevrax.org
+ + + + + + + +
#News
#Mailing-list
#Documentation
#CVS
#Bugs
#License
+
+ + +
+ + +
+Docs + +
+  + + + + + +
Documentation 
+ +
+Main Page   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Namespace Members   Compound Members   File Members   Related Pages   Search  
+

naming_client.cpp

Go to the documentation of this file.
00001 
+00008 /* Copyright, 2000 Nevrax Ltd.
+00009  *
+00010  * This file is part of NEVRAX NEL.
+00011  * NEVRAX NEL is free software; you can redistribute it and/or modify
+00012  * it under the terms of the GNU General Public License as published by
+00013  * the Free Software Foundation; either version 2, or (at your option)
+00014  * any later version.
+00015 
+00016  * NEVRAX NEL is distributed in the hope that it will be useful, but
+00017  * WITHOUT ANY WARRANTY; without even the implied warranty of
+00018  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+00019  * General Public License for more details.
+00020 
+00021  * You should have received a copy of the GNU General Public License
+00022  * along with NEVRAX NEL; see the file COPYING. If not, write to the
+00023  * Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
+00024  * MA 02111-1307, USA.
+00025  */
+00026 
+00027 //
+00028 // Includes
+00029 //
+00030 
+00031 #include "stdnet.h"
+00032 
+00033 #include "nel/net/naming_client.h"
+00034 #include "nel/net/callback_client.h"
+00035 #include "nel/net/service.h"
+00036 
+00037 
+00038 //
+00039 // Namespaces
+00040 //
+00041 
+00042 using namespace std;
+00043 using namespace NLMISC;
+00044 
+00045 
+00046 namespace NLNET {
+00047 
+00048 //
+00049 // Variables
+00050 //
+00051 
+00052 CCallbackClient *CNamingClient::_Connection = NULL;
+00053 CNamingClient::TRegServices CNamingClient::_RegisteredServices;
+00054 
+00055 static TBroadcastCallback _RegistrationBroadcastCallback = NULL;
+00056 static TBroadcastCallback _UnregistrationBroadcastCallback = NULL;
+00057 
+00058 uint    CNamingClient::_ThreadId = 0xFFFFFFFF;
+00059 
+00060 TServiceId CNamingClient::_MySId = 0;
+00061 
+00062 
+00063 std::list<CNamingClient::CServiceEntry> CNamingClient::RegisteredServices;
+00064 NLMISC::CMutex CNamingClient::RegisteredServicesMutex("CNamingClient::RegisteredServicesMutex");
+00065 
+00066 void CNamingClient::setRegistrationBroadcastCallback (TBroadcastCallback cb)
+00067 {
+00068         _RegistrationBroadcastCallback = cb;    
+00069 }
+00070 
+00071 void CNamingClient::setUnregistrationBroadcastCallback (TBroadcastCallback cb)
+00072 {
+00073         _UnregistrationBroadcastCallback = cb;  
+00074 }
+00075 
+00076 //
+00077 
+00078 //
+00079 
+00080 static bool Registered;
+00081 static TServiceId RegisteredSuccess;
+00082 static TServiceId *RegisteredSID = NULL;
+00083 
+00084 static void cbRegister (CMessage &msgin, TSockId from, CCallbackNetBase &netbase)
+00085 {
+00086         nlassert(RegisteredSID != NULL);
+00087 
+00088         msgin.serial (RegisteredSuccess);
+00089         if (RegisteredSuccess)
+00090         {
+00091                 msgin.serial (*RegisteredSID);
+00092 
+00093                 // decode the registered services at the register process
+00094                 cbRegisterBroadcast (msgin, from, netbase);
+00095         }
+00096         Registered = true;
+00097 }
+00098 
+00099 //
+00100 
+00101 static bool QueryPort;
+00102 static uint16 QueryPortPort;
+00103 
+00104 static void cbQueryPort (CMessage &msgin, TSockId from, CCallbackNetBase &netbase)
+00105 {
+00106         msgin.serial (QueryPortPort);
+00107         QueryPort = true;
+00108 }
+00109 
+00110 //
+00111 
+00112 //static bool FirstRegisteredBroadcast;
+00113 
+00114 void cbRegisterBroadcast (CMessage &msgin, TSockId from, CCallbackNetBase &netbase)
+00115 {
+00116         TServiceId size;
+00117         string name;
+00118         TServiceId sid;
+00119         vector<CInetAddress> addr;
+00120 
+00121         msgin.serial (size);
+00122 
+00123         for (TServiceId i = 0; i < size; i++)
+00124         {
+00125                 msgin.serial (name);
+00126                 msgin.serial (sid);
+00127                 msgin.serialCont (addr);
+00128 
+00129                 // add it in the list
+00130 
+00131                 std::vector<CInetAddress> addrs;
+00132                 CNamingClient::find (sid, addrs);
+00133 
+00134                 if (addrs.size() == 0)
+00135                 {
+00136                         CNamingClient::RegisteredServicesMutex.enter ();
+00137                         CNamingClient::RegisteredServices.push_back (CNamingClient::CServiceEntry (name, sid, addr));
+00138                         CNamingClient::RegisteredServicesMutex.leave ();
+00139 
+00140                         nlinfo ("NC: Registration Broadcast of the service %s-%hu '%s'", name.c_str(), (uint16)sid, vectorCInetAddressToString(addr).c_str());
+00141 
+00142                         if (_RegistrationBroadcastCallback != NULL)
+00143                                 _RegistrationBroadcastCallback (name, sid, addr);
+00144                 }
+00145                 else if (addrs.size() == 1)
+00146                 {
+00147                         CNamingClient::RegisteredServicesMutex.enter ();
+00148                         for (std::list<CNamingClient::CServiceEntry>::iterator it = CNamingClient::RegisteredServices.begin(); it != CNamingClient::RegisteredServices.end (); it++)
+00149                         {
+00150                                 if (sid == (*it).SId)
+00151                                 {
+00152                                         (*it).Name = name;
+00153                                         (*it).Addr = addr;
+00154                                         break;
+00155                                 }
+00156                         }
+00157                         CNamingClient::RegisteredServicesMutex.leave ();
+00158                         nlinfo ("NC: Registration Broadcast (update) of the service %s-%hu '%s'", name.c_str(), (uint16)sid, addr[0].asString().c_str());
+00159                 }
+00160                 else
+00161                 {
+00162                         nlstop;
+00163                 }
+00164         }
+00165 
+00166 //      FirstRegisteredBroadcast = true;
+00167 
+00168         //CNamingClient::displayRegisteredServices ();
+00169 }
+00170         
+00171 //
+00172 
+00173 void cbUnregisterBroadcast (CMessage &msgin, TSockId from, CCallbackNetBase &netbase)
+00174 {
+00175         string name;
+00176         TServiceId sid;
+00177         vector<CInetAddress> addrs;
+00178 
+00179         msgin.serial (name);
+00180         msgin.serial (sid);
+00181 
+00182         // remove it in the list, if the service is not found, ignore it
+00183 
+00184         CNamingClient::RegisteredServicesMutex.enter ();
+00185         for (std::list<CNamingClient::CServiceEntry>::iterator it = CNamingClient::RegisteredServices.begin(); it != CNamingClient::RegisteredServices.end (); it++)
+00186         {
+00187                 if ((*it).SId == sid)
+00188                 {
+00189                         // check the structure
+00190                         nlassertex ((*it).Name == name, ("%s %s",(*it).Name.c_str(), name.c_str()));
+00191 
+00192                         addrs = (*it).Addr;
+00193 
+00194                         CNamingClient::RegisteredServices.erase (it);
+00195                         break;
+00196                 }
+00197         }
+00198         CNamingClient::RegisteredServicesMutex.leave ();
+00199 
+00200         nlinfo ("NC: Unregistration Broadcast of the service %s-%hu", name.c_str(), (uint16)sid);
+00201 
+00202         // send the ACK to the NS
+00203 
+00204         CMessage msgout (CNamingClient::_Connection->getSIDA(), "ACK_UNI");
+00205         msgout.serial (sid);
+00206         CNamingClient::_Connection->send (msgout);
+00207 
+00208         // oh my god, it s my sid! but i m alive, why this f*cking naming service want to kill me? ok, i leave it alone!
+00209         if(CNamingClient::_MySId == sid)
+00210         {
+00211                 nlwarning ("Naming Service asked me to leave, I leave!");
+00212                 IService::getInstance()->exit();
+00213                 return;
+00214         }
+00215 
+00216         if (_UnregistrationBroadcastCallback != NULL)
+00217                 _UnregistrationBroadcastCallback (name, sid, addrs);
+00218 
+00219         //CNamingClient::displayRegisteredServices ();
+00220 }
+00221 
+00222 //
+00223 
+00224 static TCallbackItem NamingClientCallbackArray[] =
+00225 {
+00226         { "RG", cbRegister },
+00227         { "QP", cbQueryPort },
+00228 
+00229         { "RGB", cbRegisterBroadcast },
+00230         { "UNB", cbUnregisterBroadcast },
+00231 };
+00232 
+00233 void CNamingClient::connect( const CInetAddress &addr, CCallbackNetBase::TRecordingState rec, const vector<CInetAddress> &addresses )
+00234 {
+00235         nlassert (_Connection == NULL || _Connection != NULL && !_Connection->connected ());
+00236         _ThreadId = getThreadId ();
+00237 
+00238         if (_Connection == NULL)
+00239         {
+00240                 _Connection = new CCallbackClient( rec, "naming_client.nmr" );
+00241                 _Connection->addCallbackArray (NamingClientCallbackArray, sizeof (NamingClientCallbackArray) / sizeof (NamingClientCallbackArray[0]));
+00242         }
+00243 
+00244         _Connection->connect (addr);
+00245 
+00246 /*      // send the available addresses
+00247         CMessage msgout (_Connection->getSIDA(), "RS");
+00248         msgout.serialCont (const_cast<vector<CInetAddress>&>(addresses));
+00249         _Connection->send (msgout);
+00250         
+00251         // wait the message that contains all already connected services
+00252         FirstRegisteredBroadcast = false;
+00253         while (!FirstRegisteredBroadcast && _Connection->connected ())
+00254         {
+00255                 _Connection->update (-1);
+00256                 nlSleep (1);
+00257         }
+00258 */}
+00259 
+00260 
+00261 void CNamingClient::disconnect ()
+00262 {
+00263         checkThreadId ();
+00264         
+00265         if (_Connection != NULL)
+00266         {
+00267                 if (_Connection->connected ())
+00268                 {
+00269                         _Connection->disconnect ();
+00270                 }
+00271                 delete _Connection;
+00272                 _Connection = NULL;
+00273         }
+00274 
+00275         // we don't call unregisterAllServices because when the naming service will see the disconnection,
+00276         // it'll automatically unregister all services registered by this client.
+00277 }
+00278 
+00279 string CNamingClient::info ()
+00280 {
+00281         string res;
+00282 
+00283         if (connected ())
+00284         {
+00285                 res = "connected to ";
+00286                 res += _Connection->remoteAddress().asString();
+00287         }
+00288         else
+00289         {
+00290                 res = "Not connected";
+00291         }
+00292 
+00293         return res;
+00294 }
+00295 
+00296 bool CNamingClient::registerService (const std::string &name, const std::vector<CInetAddress> &addr, TServiceId &sid)
+00297 {
+00298         checkThreadId ();
+00299         nlassert (_Connection != NULL && _Connection->connected ());
+00300 
+00301         CMessage msgout (_Connection->getSIDA(), "RG");
+00302         msgout.serial (const_cast<std::string&>(name));
+00303         msgout.serialCont (const_cast<vector<CInetAddress>&>(addr));
+00304         sid = 0;
+00305         msgout.serial (sid);
+00306         _Connection->send (msgout);
+00307 
+00308         // wait the answer of the naming service "RG"
+00309         Registered = false;
+00310         RegisteredSID = &sid;
+00311         while (!Registered)
+00312         {
+00313                 _Connection->update (-1);
+00314                 nlSleep (1);
+00315         }
+00316         if (RegisteredSuccess)
+00317         {
+00318                 _MySId = sid;
+00319                 _RegisteredServices.insert (make_pair (*RegisteredSID, name));
+00320                 nldebug ("NC: Registered service %s-%hu at %s", name.c_str(), (uint16)sid, addr[0].asString().c_str());
+00321         }
+00322         else
+00323         {
+00324                 nlerror ("NC: Naming service refused to register service %s at %s", name.c_str(), addr[0].asString().c_str());
+00325         }
+00326 
+00327         RegisteredSID = NULL;
+00328 
+00329         return RegisteredSuccess == 1;
+00330 }
+00331 
+00332 bool CNamingClient::registerServiceWithSId (const std::string &name, const std::vector<CInetAddress> &addr, TServiceId sid)
+00333 {
+00334         checkThreadId ();
+00335         nlassert (_Connection != NULL && _Connection->connected ());
+00336 
+00337         CMessage msgout (_Connection->getSIDA(), "RG");
+00338         msgout.serial (const_cast<std::string&>(name));
+00339         msgout.serialCont (const_cast<vector<CInetAddress>&>(addr));
+00340         msgout.serial (sid);
+00341         _Connection->send (msgout);
+00342 
+00343         // wait the answer of the naming service "RGI"
+00344         Registered = false;
+00345         RegisteredSID = &sid;
+00346         while (!Registered)
+00347         {
+00348                 _Connection->update (-1);
+00349                 nlSleep (1);
+00350         }
+00351         if (RegisteredSuccess)
+00352         {
+00353                 _MySId = sid;
+00354                 _RegisteredServices.insert (make_pair (*RegisteredSID, name));
+00355                 nldebug ("NC: Registered service with sid %s-%hu at %s", name.c_str(), (uint16)RegisteredSID, addr[0].asString().c_str());
+00356         }
+00357         else
+00358         {
+00359                 nlerror ("NC: Naming service refused to register service with sid %s at %s", name.c_str(), addr[0].asString().c_str());
+00360         }
+00361 
+00362         return RegisteredSuccess == 1;
+00363 }
+00364 
+00365 void CNamingClient::resendRegisteration (const std::string &name, const std::vector<CInetAddress> &addr, TServiceId sid)
+00366 {
+00367         checkThreadId ();
+00368         nlassert (_Connection != NULL && _Connection->connected ());
+00369 
+00370         CMessage msgout (_Connection->getSIDA(), "RRG");
+00371         msgout.serial (const_cast<std::string&>(name));
+00372         msgout.serialCont (const_cast<vector<CInetAddress>&>(addr));
+00373         msgout.serial (sid);
+00374         _Connection->send (msgout);
+00375 }
+00376 
+00377 void CNamingClient::unregisterService (TServiceId sid)
+00378 {
+00379         checkThreadId ();
+00380         nlassert (_Connection != NULL && _Connection->connected ());
+00381 
+00382         CMessage msgout (_Connection->getSIDA(), "UNI");
+00383         msgout.serial (sid);
+00384         _Connection->send (msgout);
+00385 
+00386         nldebug ("NC: Unregistering service %s-%hu", _RegisteredServices[sid].c_str(), sid);
+00387         _RegisteredServices.erase (sid);
+00388 }
+00389 
+00390 void CNamingClient::unregisterAllServices ()
+00391 {
+00392         checkThreadId ();
+00393         nlassert (_Connection != NULL && _Connection->connected ());
+00394 
+00395         while (!_RegisteredServices.empty())
+00396         {
+00397                 TRegServices::iterator irs = _RegisteredServices.begin();
+00398                 TServiceId sid = (*irs).first;
+00399                 unregisterService (sid);
+00400         }
+00401 }
+00402 
+00403 uint16 CNamingClient::queryServicePort ()
+00404 {
+00405         checkThreadId ();
+00406         nlassert (_Connection != NULL && _Connection->connected ());
+00407 
+00408         CMessage msgout (_Connection->getSIDA(), "QP");
+00409         _Connection->send (msgout);
+00410 
+00411         // wait the answer of the naming service "QP"
+00412         QueryPort = false;
+00413         while (!QueryPort)
+00414         {
+00415                 _Connection->update (-1);
+00416                 nlSleep (1);
+00417         }
+00418 
+00419         nlinfo ("NC: Received the answer of the query port (%hu)", QueryPortPort);
+00420 
+00421         return QueryPortPort;
+00422 }
+00423 
+00424 bool CNamingClient::lookup (const std::string &name, CInetAddress &addr)
+00425 {
+00426         nlassert (_Connection != NULL && _Connection->connected ());
+00427 
+00428         vector<CInetAddress> addrs;
+00429         find (name, addrs);
+00430 
+00431         if (addrs.size()==0)
+00432                 return false;
+00433 
+00434         nlassert (addrs.size()==1);
+00435         addr = addrs[0];
+00436 
+00437         return true;
+00438 }
+00439 
+00440 bool CNamingClient::lookup (TServiceId sid, CInetAddress &addr)
+00441 {
+00442         nlassert (_Connection != NULL && _Connection->connected ());
+00443 
+00444         vector<CInetAddress> addrs;
+00445         find (sid, addrs);
+00446 
+00447         if (addrs.size()==0)
+00448                 return false;
+00449 
+00450         nlassert (addrs.size()==1);
+00451         addr = addrs[0];
+00452         
+00453         return true;
+00454 }
+00455 
+00457 bool CNamingClient::lookupAlternate (const std::string &name, CInetAddress &addr)
+00458 {
+00459         nlassert (_Connection != NULL && _Connection->connected ());
+00460 
+00461         // remove it from his local list
+00462         
+00463         RegisteredServicesMutex.enter ();
+00464         for (std::list<CServiceEntry>::iterator it = RegisteredServices.begin(); it != RegisteredServices.end (); it++)
+00465         {
+00466                 if ((*it).Addr[0] == addr)
+00467                 {
+00468                         RegisteredServices.erase (it);
+00469                         break;
+00470                 }
+00471         }
+00472         RegisteredServicesMutex.leave ();
+00473 
+00474         vector<CInetAddress> addrs;
+00475         find (name, addrs);
+00476 
+00477         if (addrs.size()==0)
+00478                 return false;
+00479 
+00480         nlassert (addrs.size()==1);
+00481         addr = addrs[0];
+00482 
+00483         return true;
+00484 }
+00485 
+00486 void CNamingClient::lookupAll (const std::string &name, std::vector<CInetAddress> &addrs)
+00487 {
+00488         nlassert (_Connection != NULL && _Connection->connected ());
+00489 
+00490         find (name, addrs);
+00491 }
+00492 
+00493 bool CNamingClient::lookupAndConnect (const std::string &name, CCallbackClient &sock)
+00494 {
+00495         nlassert (_Connection != NULL && _Connection->connected ());
+00496 
+00497         // look up for service
+00498         CInetAddress servaddr;
+00499         
+00500         // if service not found, return false
+00501         if (!CNamingClient::lookup (name, servaddr))
+00502                 return false;
+00503 
+00504         do
+00505         {
+00506                 try
+00507                 {
+00508                         // try to connect to the server
+00509                         sock.connect (servaddr);
+00510 
+00511                         // connection succeeded
+00512                         return true;
+00513                 }
+00514                 catch (ESocketConnectionFailed &e)
+00515                 {
+00516                         nldebug( "Connection to %s failed: %s, tring another service if available", servaddr.asString().c_str(), e.what() );
+00517 
+00518                         // try another server and if service is not found, return false
+00519                         if (!CNamingClient::lookupAlternate (name, servaddr))
+00520                                 return false;
+00521                 }
+00522         }
+00523         while (true);
+00524 }
+00525 
+00526 
+00527 
+00528 void CNamingClient::update ()
+00529 {
+00530         checkThreadId ();
+00531         // get message for naming service (new registration for example)
+00532         if (_Connection != NULL && _Connection->connected ())
+00533                 _Connection->update ();
+00534 }
+00535 
+00536 void CNamingClient::checkThreadId ()
+00537 {
+00538         if (getThreadId () != _ThreadId)
+00539         {
+00540                 nlerror ("You try to access to the CNamingClient with 2 differents thread (%d and %d)", _ThreadId, getThreadId());
+00541         }
+00542 }
+00543 
+00544 
+00545 //
+00546 // Commands
+00547 //
+00548 
+00549 NLMISC_COMMAND(services, "displays registered services", "")
+00550 {
+00551         if(args.size() != 0) return false;
+00552 
+00553         CNamingClient::displayRegisteredServices (&log);
+00554 
+00555         return true;
+00556 }
+00557 
+00558 } // NLNET
+
+ + +
                                                                                                                                                                    +
+ + -- cgit v1.2.1