Main Page   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members   Related Pages  

XFuBluetoothNetwork.cpp

Go to the documentation of this file.
00001 /*!
00002  * \file
00003  * X-Forge Engine <br>
00004  * Copyright 2000-2002 Fathammer Ltd
00005  *
00006  * \brief Default implementation for a Bluetooth communication manager.
00007  *
00008  * $Id: XFuBluetoothNetwork.cpp,v 1.14 2003/10/15 07:56:53 slehti Exp $
00009  * $Date: 2003/10/15 07:56:53 $
00010  * $Revision: 1.14 $
00011  */
00012 
00013 #include <xforge.h>
00014 
00015 #include <xfcore/net/XFcBtHandler.h>
00016 #include <xfcore/net/XFcBtClientWin.h>
00017 #include <xfcore/net/XFcObjectDataFrame.h>
00018 #include <xfcore/net/XFcCommunicationScheduler.h>
00019 #include <xfcore/net/XFcCommunicationConstants.h>
00020 #include <xfcore/net/socket/XFcSocketConstants.h>
00021 #include <xfcore/net/socket/XFcBtAddress.h>
00022 #include <xfcore/net/XFcUnknownSender.h>
00023 #include <xfcore/net/XFcClientLost.h>
00024 #include <xfcore/net/XFcDataReceiver.h>
00025 #include <xfcore/net/XFcObjectDataFrame.h>
00026 #include <xfcore/net/socket/XFcHostEntry.h>
00027 #include <xfcore/net/socket/XFcBtHostResolver.h>
00028 #include <xfcore/net/socket/XFcBtAdvertiser.h>
00029 #include <xfcore/net/XFcUdpEngine.h>
00030 #include <xfcore/net/socket/XFcBtCommService.h>
00031 #include <xfcore/net/socket/XFcBtServerSearch.h>
00032 #include <xfcore/net/socket/XFcName.h>
00033 #include <xfutil/XFuSerializable.h>
00034 #include <xfutil/XFuNetwork.h>
00035 #include <xfutil/XFuNetworkEventHandler.h>
00036 #include <xfutil/XFuBluetoothNetwork.h>
00037 
00038 
00039 XFuBluetoothNetwork * XFuBluetoothNetwork::create()
00040 {
00041     XFuBluetoothNetwork * manager = new XFuBluetoothNetwork;
00042     if (manager != NULL && !manager->init())
00043     {
00044         delete manager;
00045         return NULL;
00046     }
00047     return manager;
00048 }
00049 
00050 
00051 XFuBluetoothNetwork::XFuBluetoothNetwork()
00052 {
00053     mNetworkEventHandlers = NULL;
00054     mCommunicationScheduler = NULL;
00055     mCommunicationHandler = NULL;
00056     mDefaultDataReceiver = NULL;
00057     mHostResolver = NULL;
00058     mCommunicationService = NULL;
00059    
00060     mAcceptGameToken = 0;
00061     mCommunicationHandlerId = -1;
00062     mGamePort = 0;
00063     mClientId = -1;
00064     mClient = NULL;
00065     mService = NULL;
00066     mBtServerSearch = NULL;
00067 }
00068 
00069 
00070 XFuBluetoothNetwork::~XFuBluetoothNetwork()
00071 {
00072     closeService();    
00073     deleteAllClients();
00074     removeAllEventHandlers();
00075 
00076     delete mService;
00077     delete mHostResolver;
00078     delete mNetworkEventHandlers;
00079     delete mCommunicationHandler;
00080     delete mBtServerSearch;
00081 }
00082 
00083 
00084 INT XFuBluetoothNetwork::init()
00085 {
00086     mCommunicationScheduler = (XFcCommunicationScheduler *)XFcCore::getCommunicationScheduler();
00087     if (mNetworkEventHandlers == NULL)
00088         mNetworkEventHandlers = XFuDynamicArray<XFuNetworkEventHandler*>::create(5);
00089 
00090     if (mCommunicationScheduler == NULL ||
00091         mNetworkEventHandlers == NULL) return 0;
00092 
00093     return 1;
00094 
00095 }
00096 
00097 
00098 void XFuBluetoothNetwork::runCommunicationScheduler()
00099 {
00100     mCommunicationScheduler->runScheduler();
00101 }
00102 
00103 
00104 void XFuBluetoothNetwork::reset()
00105 {
00106     closeService();
00107     deleteAllClients();
00108     removeAllEventHandlers();   
00109     mAcceptGameToken = 0;
00110     init();
00111 
00112 }
00113 
00114 
00115 INT XFuBluetoothNetwork::initEnable(UINT16 aPort, INT aIsServer)
00116 {
00117     closeService();
00118     deleteAllClients();
00119 
00120     mService = XFcBtCommService::create();
00121     mGamePort = aPort;
00122 
00123     // Are we Bluetooth server, bt-slave.
00124     if (aIsServer)
00125     {
00126         if (aPort == 0 && mService)
00127             mGamePort = mService->getFirstFreeRFCOMMPort();
00128     }
00129     else
00130     {
00131         // Create piconet. Works only with master device.
00132         mService->createPiconet();
00133         mService->lockPiconet();
00134     }
00135     
00136     if (mGamePort == XFCNET_NOT_SUPPORTED)
00137         mGamePort = 0;
00138 
00139     mCommunicationHandler = XFcBtHandler::create(aIsServer);
00140     
00141     return (mCommunicationHandler && mService) ? 1 : 0;
00142 }
00143 
00144 
00145 INT XFuBluetoothNetwork::enableClientService()
00146 {
00147     INT error = 0;
00148 
00149     if (initEnable(0, 0))
00150     {
00151         mCommunicationHandler->setUnknownSenderHandler(this);
00152         mCommunicationHandler->setClientLost(this);
00153 
00154         mCommunicationHandlerId = mCommunicationScheduler->addCommunicationHandler(mCommunicationHandler);
00155         error = 1;
00156     }
00157     return error;
00158 }
00159 
00160 
00161 INT XFuBluetoothNetwork::enableServerService(UINT16 aPort)
00162 {    
00163     XFcBtAddress *address = XFcBtAddress::create();
00164     XFcBtClientWin *client = XFcBtClientWin::create(NULL);
00165 
00166     if (address && client && initEnable(aPort, 1))
00167     {
00168 
00169         address->setPort(mGamePort);
00170 
00171         // Max client count must be more than 1
00172         INT32 maxClients = 2;
00173 
00174         // Open server, will return 1 if success else 0
00175         if (mCommunicationHandler->openServer(*address, maxClients))
00176         {
00177             mCommunicationHandler->setUnknownSenderHandler(this);
00178             mCommunicationHandler->setClientLost(this);
00179             
00180 
00181             mCommunicationHandlerId = mCommunicationScheduler->addCommunicationHandler(mCommunicationHandler);
00182             mCommunicationHandler->listenConnection(*client);
00183 
00184             INT32 clientId = mCommunicationScheduler->addClient(client);
00185 
00186             if (clientId != XFCNET_CLIENTADD_ERROR)
00187             {
00188 
00189                 mClient = client;
00190                 mClientId = clientId;
00191                 delete address;
00192                 address = NULL;
00193 
00194                 return 1;
00195             }
00196         }
00197     }
00198     delete address;
00199     address = NULL;
00200     delete client;
00201     client = NULL;
00202 
00203     mClient = NULL;
00204     mClientId = -1;
00205     return 0;
00206 }
00207 
00208  
00209 void XFuBluetoothNetwork::closeService()
00210 {   
00211     // Unlock and destroy piconet if any.
00212     mService->unlockPiconet();
00213     mService->destroyPiconet();
00214     
00215     stopDeviceDiscovery();
00216     stopServerDiscovery();
00217     stopAdvertiser();
00218 
00219     if (mCommunicationHandler != NULL)
00220     {
00221         mCommunicationHandler->closeService();
00222         mCommunicationScheduler->removeCommunicationHandler(mCommunicationHandlerId);
00223         delete mCommunicationHandler;
00224         mCommunicationHandler = NULL;
00225     }
00226     delete mService;
00227     mService = NULL;
00228 }
00229 
00230 
00231 UINT32 XFuBluetoothNetwork::getAcceptGameToken()
00232 {
00233     return mAcceptGameToken;
00234 }
00235 
00236 
00237 void XFuBluetoothNetwork::setAcceptGameToken(UINT32 aAcceptGameToken)
00238 {
00239     mAcceptGameToken = aAcceptGameToken;
00240 }
00241 
00242 
00243 void XFuBluetoothNetwork::sendGameConnectPacket(INT32 aClientId, UINT32 aGameToken)
00244 {
00245     XFcObjectDataFrame *frame = getPacketFrame(aClientId, XFCNET_NONGUARANTEED);
00246     if (frame)
00247     {
00248         frame->setReceiverId(0);
00249         void *buffer = frame->lock();
00250         if (buffer)
00251         {
00252             memcpy(buffer, &aGameToken, 4);
00253             frame->setPacketSize(4);
00254         }
00255         frame->unlock();
00256     }
00257 }
00258 
00259 
00260 void XFuBluetoothNetwork::deleteAllClients()
00261 {
00262     if (!mClient)
00263         return;
00264 
00265     if (!mCommunicationScheduler)
00266         return;
00267 
00268     mCommunicationScheduler->removeClient(mClientId);
00269     mClient->deinitializeClient();
00270     delete mClient;
00271     mClient = NULL;
00272     mClientId = -1;
00273 }
00274 
00275 
00276 void XFuBluetoothNetwork::removeAllClients()
00277 {
00278     if (!mCommunicationHandler)
00279         return;
00280 
00281     removeClient(mClientId);
00282 }
00283 
00284 
00285 XFcDataReceiver * XFuBluetoothNetwork::getDefaultDataReceiver()
00286 {
00287     return mDefaultDataReceiver;
00288 }
00289 
00290 
00291 void XFuBluetoothNetwork::setDefaultDataReceiver(XFcDataReceiver *aReceiver)
00292 {
00293     mDefaultDataReceiver = aReceiver;
00294     mCommunicationScheduler->setDataReceiver(aReceiver);
00295 }
00296 
00297 
00298 XFcDataReceiver * XFuBluetoothNetwork::getDataReceiver(UINT32 aId)
00299 {
00300     return mCommunicationScheduler->getDataReceiver(aId);
00301 }
00302 
00303 
00304 INT XFuBluetoothNetwork::addDataReceiver(UINT32 aId, XFcDataReceiver *aReceiver)
00305 {
00306     return mCommunicationScheduler->addDataReceiver(aId, aReceiver);
00307 }
00308 
00309 
00310 XFcDataReceiver * XFuBluetoothNetwork::removeDataReceiver(UINT32 aId)
00311 {
00312     return mCommunicationScheduler->removeDataReceiver(aId);
00313 }
00314 
00315 
00316 void XFuBluetoothNetwork::addEventHandler(XFuNetworkEventHandler *aHandler)
00317 {
00318     mNetworkEventHandlers->put(aHandler);
00319 }
00320 
00321 
00322 void XFuBluetoothNetwork::removeEventHandler(XFuNetworkEventHandler *aHandler)
00323 {
00324     mNetworkEventHandlers->remove(aHandler);
00325 }
00326 
00327 
00328 void XFuBluetoothNetwork::removeAllEventHandlers()
00329 {
00330     while (!mNetworkEventHandlers->isEmpty()) mNetworkEventHandlers->remove();
00331 }
00332 
00333 
00334 XFcClientCommWin * XFuBluetoothNetwork::getClient(INT32 /*aClientId*/)
00335 {
00336     return mClient;
00337 }
00338 
00339 
00340 INT32 XFuBluetoothNetwork::addClient(XFcAddress *aAddress, INT32 /*aTimeoutTime*/)
00341 {
00342     XFcBtClientWin *client = NULL;
00343     INT32 clientId = -1;
00344 
00345     if (!aAddress)
00346         return -1;
00347 
00348     if ((client = XFcBtClientWin::create(aAddress)) == NULL)
00349         return -1;
00350 
00351     switch (aAddress->getType())
00352     {
00353         case XFCNET_AFBT:
00354             if (client->openClient() != -1)
00355             {
00356                 clientId = mCommunicationScheduler->addClient(client);
00357                 if (clientId != XFCNET_CLIENTADD_ERROR && clientId != XFCNET_ERROR)
00358                 {
00359                     mClient = client;
00360                 }
00361             }
00362 
00363             break;
00364         default:
00365             XFcCore::systemPanic(XFCSTR("This address type is not supported"));
00366             break;
00367     }
00368 
00369     if (clientId == -1)
00370         delete client;
00371 
00372     mClientId = clientId;
00373     return clientId;
00374 }
00375 
00376 
00377 void XFuBluetoothNetwork::removeClient(INT32 aClientId)
00378 {
00379     INT32 cId = 0;
00380 
00381     // If communication handler is not created we do not have anything to do.
00382     if (!mCommunicationHandler)
00383         return;
00384 
00385     if (mClient == NULL)
00386         return;
00387 
00388     // Remove client and deinitialize it
00389     mCommunicationScheduler->removeClient(aClientId);
00390     mClient->deinitializeClient();
00391 
00392     delete mClient;
00393     mClient = NULL;
00394     mClientId = -1;
00395 
00396     // Listening client is created to backbuffer for incoming connections.
00397     // If client is removed we create new for new connection.
00398     if (mCommunicationHandler->isServer())
00399     {
00400         XFcBtClientWin *client = NULL;
00401         if ((client = XFcBtClientWin::create(NULL)) != NULL)
00402         {
00403             mCommunicationHandler->listenConnection(*client);
00404             cId = mCommunicationScheduler->addClient(client);
00405 
00406             if (cId != XFCNET_CLIENTADD_ERROR && cId != XFCNET_ERROR)
00407             {
00408                 mClientId = cId;
00409                 mClient = client;
00410             }
00411             else
00412                 XFcCore::systemPanic(XFCSTR("removeClient(), add client"));
00413         }
00414         else
00415             XFcCore::systemPanic(XFCSTR("removeClient(), new listener"));
00416     }
00417 }
00418 
00419 
00420 INT32 XFuBluetoothNetwork::getRoundTripTime(INT32 aClientId)
00421 {
00422     return mCommunicationScheduler->getRoundTripTime(aClientId);
00423 }
00424 
00425 
00426 XFcObjectDataFrame * XFuBluetoothNetwork::getPacketFrame(INT32 aClientId, XFCNET_MESSAGE_SLOT aSlot)
00427 {
00428     return mCommunicationScheduler->getPacketFrame(aClientId, aSlot);
00429 }
00430 
00431 
00432 XFcObjectDataFrame * XFuBluetoothNetwork::getRecentStateFrame(INT32 aClientId, INT32 aRecentId)
00433 {
00434     return mCommunicationScheduler->getRecentStateFrame(aClientId, aRecentId);
00435 }
00436 
00437 
00438 void XFuBluetoothNetwork::removeRecentStateFrame(INT32 aClientId, INT32 aRecentId)
00439 {
00440     mCommunicationScheduler->removeRecentStateFrame(aClientId, aRecentId);
00441 }
00442 
00443 
00444 INT32 XFuBluetoothNetwork::send(INT32 aClientId, UINT32 aReceiverId, XFCNET_MESSAGE_SLOT aSlot, XFuSerializable *aSerializable)
00445 {
00446     XFcObjectDataFrame *frame = getPacketFrame(aClientId, aSlot);
00447     INT32 size = -1;
00448     if (frame)
00449     {
00450 
00451         void *buffer = frame->lock();
00452         if (buffer)
00453         {
00454             size = aSerializable->serialize((CHAR8*)buffer, frame->sizeofBuffer());
00455             // If size is set to -1 XForge does not send the frame and frame is released.
00456             frame->setPacketSize(size);
00457             frame->setReceiverId(aReceiverId);
00458 
00459         }
00460         frame->unlock();
00461     }
00462     return size;
00463 }
00464 
00465 
00466 INT32 XFuBluetoothNetwork::sendRecentState(INT32 aClientId, UINT32 aReceiverId, INT32 aRecentId, XFuSerializable *aSerializable)
00467 {
00468     XFcObjectDataFrame *frame = getRecentStateFrame(aClientId, aRecentId);
00469     INT32 size = -1;
00470 
00471     if (frame)
00472     {
00473         void *buffer = frame->lock();
00474         if (buffer)
00475         {
00476             size = aSerializable->serialize((CHAR8*)buffer, frame->sizeofBuffer());
00477             frame->setPacketSize(size);
00478             frame->setReceiverId(aReceiverId);
00479 
00480         }
00481         frame->unlock();
00482     }
00483     return size;
00484 }
00485 
00486 
00487 void XFuBluetoothNetwork::clientLost(INT32 aClientId)
00488 {
00489     removeClient(aClientId);
00490 
00491     INT32 handlersNum = mNetworkEventHandlers->size();
00492     INT32 i;
00493 
00494     for (i = 0; i < handlersNum; i++)
00495     {
00496         mNetworkEventHandlers->get(i)->handleClientLost(aClientId);
00497     }
00498 }
00499 
00500 
00501 INT XFuBluetoothNetwork::handleSender(const void *aAddress, const CHAR8 *aData, INT32 aLen)
00502 {
00503     // Used magic number mAcceptGameToken here.
00504     // Make sure that gameToken is not addjusted with same value than mAcceptGameToken is.
00505     UINT32 gameToken = ~mAcceptGameToken;
00506 
00507     if (((XFcAddress *)aAddress)->getType() == (INT32)XFCNET_AFBT && aLen == 4)
00508     {
00509         // Get packet data
00510         memcpy(&gameToken, aData, 4);
00511 
00512         // Test if packet data is game connect token packet
00513         if (gameToken == mAcceptGameToken)
00514         {
00515             if (mClient->isClientActive() == XFCNET_BT_LINESTATUS_ONHOLD)
00516             {
00517                 // Accept client connection
00518                 mClient->acceptConnection(1);
00519 
00520                 INT32 i;
00521                 for (i = 0; i < (INT32)mNetworkEventHandlers->size(); i++)
00522                 {
00523                     // Notify event handler
00524                     mNetworkEventHandlers->get(i)->handleClientAccepted(i);
00525 
00526                 } 
00527             }
00528         }
00529     }
00530     if (((XFcAddress *)aAddress)->getType() != (INT32)XFCNET_AFBT ||
00531         aLen != 4 ||
00532         gameToken != mAcceptGameToken)
00533     {
00534 
00535         if (mClient->isClientActive() == XFCNET_BT_LINESTATUS_ONHOLD)
00536         {
00537             // Disconnect client
00538             mClient->acceptConnection(0);
00539 
00540             // Remove client
00541             removeClient(mClientId);
00542         }
00543     }
00544     return 0;
00545 }
00546 
00547 
00548 INT XFuBluetoothNetwork::startDeviceDiscovery()
00549 {
00550     // Stop device discovery
00551     stopDeviceDiscovery();
00552 
00553     // Delete host resolver
00554     if (!mHostResolver)
00555         mHostResolver = XFcBtHostResolver::create();
00556 
00557     // Do the device discovery, async found devices are returned througth deviceDiscovery callback.
00558     if (mHostResolver)
00559         return (mHostResolver->inquiry(this) == XFCNET_ERROR) ? 0 : 1;
00560 
00561     return 0;
00562 }
00563 
00564 
00565 void XFuBluetoothNetwork::stopDeviceDiscovery()
00566 {
00567     if (mHostResolver)
00568         mHostResolver->cancelInquiry();
00569 }
00570 
00571 
00572 INT XFuBluetoothNetwork::startServerDiscovery(const XFcBtUUID &aUuid, const XFcBtAddress *aAddress)
00573 {    
00574     INT retval = 0;
00575     
00576     if (!mService)
00577         return 0;
00578 
00579     mUUID = aUuid;
00580     
00581     if (aAddress)
00582     {
00583         // Have to fix this.
00584         XFcAdvertiser *advr = NULL;
00585         if ((advr = XFcBtAdvertiser::create(*aAddress, NULL, 0)) != NULL)
00586             retval = mService->inquiry(*advr, this, &mUUID);
00587         delete advr;
00588         return retval;
00589     }
00590     else
00591     {
00592         delete mBtServerSearch;
00593         if ((mBtServerSearch = XFcBtServerSearch::create()) != NULL)
00594             return (mBtServerSearch->inquiry(this, mUUID) == XFCNET_ERROR) ? 0 : 1;
00595     }
00596     return retval;
00597 }
00598 
00599 
00600 void XFuBluetoothNetwork::stopServerDiscovery()
00601 {   
00602     if (mService)
00603         mService->cancelInquiry();
00604 
00605     if (mBtServerSearch)
00606         mBtServerSearch->cancelInquiry();
00607 
00608     delete mBtServerSearch;
00609     mBtServerSearch = NULL;   
00610 }
00611 
00612 
00613 void XFuBluetoothNetwork::deviceDiscovery(const XFcLinkedList<XFcHostEntry *> &aHostEntry)
00614 {
00615     XFcLinkedList<XFcHostEntry *>::forwardIterator it;
00616     INT32 handlersNum = mNetworkEventHandlers->size();
00617     INT32 i;
00618 
00619     if (aHostEntry.size() != 0)
00620     {
00621         for (it = aHostEntry.forwardBegin(); it != aHostEntry.forwardEnd(); it++)
00622         {
00623             for (i = 0; i < handlersNum; ++i)
00624                 mNetworkEventHandlers->get(i)->handleDeviceDiscovered(it.getData());
00625         }
00626     }
00627     else
00628     {
00629         for (i = 0; i < handlersNum; ++i)
00630             mNetworkEventHandlers->get(i)->handleDeviceDiscovered(NULL);
00631     }
00632 }
00633 
00634 
00635 void XFuBluetoothNetwork::deviceDiscovery(const XFcLinkedList<XFcAdvertiser *> &aAdvertiser)
00636 {
00637     XFcLinkedList<XFcAdvertiser *>::forwardIterator it;
00638     INT32 handlersNum = mNetworkEventHandlers->size();
00639     INT32 i;
00640 
00641     if (aAdvertiser.size() != 0)
00642     {
00643         for (it = aAdvertiser.forwardBegin(); it != aAdvertiser.forwardEnd(); it++)
00644         {
00645             for (i = 0; i < handlersNum; i++)
00646                 mNetworkEventHandlers->get(i)->handleAdvertiseDiscovered(it.getData());
00647         }
00648     }
00649     else
00650     {
00651         for (i = 0; i < handlersNum; ++i)
00652             mNetworkEventHandlers->get(i)->handleAdvertiseDiscovered(NULL);
00653     }
00654 
00655 }
00656 
00657 
00658 INT XFuBluetoothNetwork::startAdvertiser(const XFcBtUUID &aUuid, const CHAR8 *aMessage)
00659 {    
00660     XFcBtAdvertiser *advertise = NULL;
00661     
00662     if (!mService)
00663         return 0;
00664 
00665     if ((advertise = XFcBtAdvertiser::create()) == NULL)
00666         return 0;
00667 
00668     mUUID = aUuid;
00669     
00670     // Create default message if not given any
00671     if (aMessage == NULL)
00672         advertise->setMessageHeader("X-Forge server", 14);
00673     else
00674         advertise->setMessageHeader(aMessage, strlen(aMessage));
00675 
00676     // Set game port for advertiser
00677     advertise->setGamePort(mGamePort);
00678 
00679     advertise->setAvailability(0xff); // Fully available.
00680 
00681     INT error = mService->advertise(*advertise, &mUUID);
00682 
00683     delete advertise;
00684 
00685     return (error == XFCNET_ERROR) ? 0 : 1;
00686     
00687 }
00688 
00689 
00690 void XFuBluetoothNetwork::stopAdvertiser()
00691 {   
00692     if (!mService)
00693         return;
00694 
00695     mService->cancelAdvertise();
00696 }
00697 
00698 
00699 INT XFuBluetoothNetwork::deviceLocalName(XFcName &aName)
00700 {
00701     // Delete host resolver
00702     if (!mHostResolver)
00703         mHostResolver = XFcBtHostResolver::create();
00704 
00705     // Do the device discovery, async found devices are returned througth deviceDiscovery callback.
00706     if (mHostResolver)
00707     {
00708         INT error = mHostResolver->localName(aName);
00709 
00710         if (error != XFCNET_ERROR)
00711         {
00712             if (aName.mLen < 0x40)
00713                 aName.mName[aName.mLen] = '\0';
00714 
00715             return 1;
00716         }
00717     }
00718     return 0;
00719 }

   
X-Forge Documentation
Confidential
Copyright © 2002-2003 Fathammer
   
Documentation generated
with doxygen
by Dimitri van Heesch