Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/branches/network/src/lib/network/network_game_manager.cc @ 7380

Last change on this file since 7380 was 7354, checked in by patrick, 18 years ago

orxonox: only a small change to the net manager

File size: 24.6 KB
Line 
1/*
2   orxonox - the future of 3D-vertical-scrollers
3
4   Copyright (C) 2004 orx
5
6   This program is free software; you can redistribute it and/or modify
7   it under the terms of the GNU General Public License as published by
8   the Free Software Foundation; either version 2, or (at your option)
9   any later version.
10
11### File Specific:
12   main-programmer: Benjamin Wuest
13   co-programmer: ...
14*/
15
16
17/* this is for debug output. It just says, that all calls to PRINT() belong to the DEBUG_MODULE_NETWORK module
18   For more information refere to https://www.orxonox.net/cgi-bin/trac.cgi/wiki/DebugOutput
19*/
20#define DEBUG_MODULE_NETWORK
21
22#include "util/loading/factory.h"
23#include "state.h"
24#include "class_list.h"
25
26#include "network_stream.h"
27#include "shared_network_data.h"
28#include "converter.h"
29
30#include "playable.h"
31#include "player.h"
32
33#include "game_world.h"
34
35#include "network_game_manager.h"
36
37
38/* using namespace std is default, this needs to be here */
39using namespace std;
40
41NetworkGameManager* NetworkGameManager::singletonRef = NULL;
42
43/*!
44 * Standard constructor
45 */
46NetworkGameManager::NetworkGameManager()
47  : Synchronizeable()
48{
49  PRINTF(0)("START\n");
50
51  /* set the class id for the base object */
52  this->setClassID(CL_NETWORK_GAME_MANAGER, "NetworkGameManager");
53
54  hasRequestedWorld = false;
55  this->setSynchronized(true);
56}
57
58/*!
59 * Standard destructor
60 */
61NetworkGameManager::~NetworkGameManager()
62{
63  for ( int i = 0; i<outBuffer.size(); i++)
64  {
65    if ( outBuffer[i].buffer )
66      delete outBuffer[i].buffer;
67  }
68
69}
70
71
72int NetworkGameManager::writeBytes(const byte* data, int length, int sender)
73{
74  int i = 0;
75  byte b;
76
77  while ( i<length )
78  {
79    b = data[i++];
80
81    /**************** Commands only processed by servers ****************/
82    if ( isServer() )
83    {
84      if ( b == NET_REQUEST_CREATE )
85      {
86        if ( !handleRequestCreate( i, data, length, sender ) )
87          return i;
88        continue;
89      }
90      else if ( b == NET_REQUEST_REMOVE )
91      {
92        if ( !handleRequestRemove( i, data, length, sender ) )
93          return i;
94        continue;
95      }
96      else if ( b == NET_REQUEST_PNODE_PATH )
97      {
98        if ( !handleRequestPNodePath( i, data, length, sender ) )
99          return i;
100        continue;
101      }
102    }
103    else
104    {
105      /**************** Commands only processed by clients ****************/
106      if ( b == NET_CREATE_ENTITY )
107      {
108        PRINTF(0)("CREATE_ENTITY\n");
109        if ( !handleCreateEntity( i, data, length, sender ) )
110          return i;
111        continue;
112      }
113      else if ( b == NET_REMOVE_ENTITY )
114      {
115        if ( !handleRemoveEntity( i, data, length, sender ) )
116          return i;
117        continue;
118      }
119      else if ( b == NET_CREATE_ENTITY_LIST )
120      {
121        if ( !handleCreateEntityList( i, data, length, sender ) )
122          return i;
123        continue;
124      }
125      else if ( b == NET_REMOVE_ENTITY_LIST )
126      {
127        if ( !handleRemoveEntityList( i, data, length, sender ) )
128          return i;
129        continue;
130      }
131      else if ( b == NET_YOU_ARE_ENTITY )
132      {
133        if ( !handleYouAreEntity( i, data, length, sender ) )
134          return i;
135        continue;
136      }
137    }
138
139    /**************** Commands processed by servers and clients ****************/
140    if ( b == NET_REQUEST_ENTITY_LIST )
141    {
142      sendEntityList( sender );
143      continue;
144    }
145    else if ( b == NET_REQUEST_SYNC )
146    {
147      if ( !handleRequestSync( i, data, length, sender ) )
148        return i;
149      continue;
150    }
151
152
153    PRINTF(1)("Network is asynchronous: couldn't decode the command sent by %i\n", sender);
154    PRINTF(1)("Probably this is because the network protocol has different \n");
155    PRINTF(1)("versions or there occured an error in the sending algorithm\n");
156    PRINTF(1)("Data is not in the right format! i=%d\n", i);
157    return i;
158  }
159
160  return i;
161}
162
163int NetworkGameManager::readBytes(byte* data, int maxLength, int * reciever)
164{
165  if ( !isServer() && !hasRequestedWorld )
166  {
167    assert( maxLength >= 1 );
168    data[0] = NET_REQUEST_ENTITY_LIST;
169    hasRequestedWorld = true;
170    return 1;
171  }
172
173  for ( int i = 0; i<outBuffer.size(); i++ )
174  {
175    *reciever = i;
176    if ( outBuffer[i].length>0 )
177    {
178      int nbytes = outBuffer[i].length;
179      outBuffer[i].length = 0;
180
181      if ( nbytes > maxLength )
182      {
183        PRINTF(1)("OutBuffer.length (%d) > (%d) networkStreamBuffer.maxLength\n", nbytes, maxLength);
184        return 0;
185      }
186
187      memcpy(data, outBuffer[i].buffer, nbytes);
188      return nbytes;
189    }
190  }
191
192  return 0;
193}
194
195void NetworkGameManager::writeDebug() const
196{
197}
198
199void NetworkGameManager::readDebug() const
200{
201}
202
203
204/*!
205 * Checks whether this is connected to a server or a client
206 * and afterwards creates the needed entity
207 * @param classID: The ID of the class of which an entity should be created
208 */
209int NetworkGameManager::createEntity( ClassID classID, int owner )
210{
211  if ( this->isServer())
212  {
213    if ( SharedNetworkData::getInstance()->getNewUniqueID() < 0 )
214    {
215      PRINTF(1)("Cannot create entity! There are no more uniqueIDs left!\n");
216      return -1;
217    }
218    return this->executeCreateEntity( classID, SharedNetworkData::getInstance()->getNewUniqueID(), owner );
219  }
220  else
221  {
222    this->requestCreateEntity( classID );
223    return -1;
224  }
225}
226
227
228/*!
229 * Checks whether this is connected to a server or a client
230 * and afterwards creates the needed entity
231 * @param classID: The ID of the class of which an entity should be created
232 */
233BaseObject* NetworkGameManager::createEntity(const TiXmlElement* element)
234{
235  if ( this->isServer() )
236  {
237    if ( SharedNetworkData::getInstance()->getNewUniqueID() < 0 )
238    {
239      PRINTF(1)("Cannot create entity! There are no more uniqueIDs left!\n");
240      return NULL;
241    }
242
243    BaseObject * b = Factory::fabricate( element );
244
245    if ( !b )
246    {
247      PRINTF(1)("Could not fabricate Object with className %s\n", element->Value() );
248      return NULL;
249    }
250
251
252    if ( b->isA(CL_SYNCHRONIZEABLE) )
253    {
254      Synchronizeable * s = dynamic_cast<Synchronizeable*>(b);
255      s->setUniqueID( SharedNetworkData::getInstance()->getNewUniqueID() );
256      s->setOwner( 0 );
257      // all entities created via this function are added automaticaly to the synchronizeable list
258      s->setSynchronized(true);
259      return b;
260    }
261    else
262    {
263      PRINTF(1)("Class %s is not a synchronizeable!\n", b->getClassName() );
264      delete b;
265    }
266
267  }
268  else
269
270  {
271    PRINTF(1)("This node is not a server and cannot create id %x\n", element->Value());
272  }
273  return NULL;
274}
275
276
277/*!
278 * Checks whether this is connected to a server or a client
279 * and afterwards removes the specified entity
280 * @param uniqueID: The ID of the entity object which should be removed
281 */
282void NetworkGameManager::removeEntity(int uniqueID)
283{
284  if ( this->isServer() )
285  {
286    this->executeRemoveEntity( uniqueID );
287  }
288  else
289  {
290    this->requestRemoveEntity( uniqueID );
291  }
292}
293
294
295
296/*!
297 * Creates the needed entity on the server if possible
298 * @param classID: The ID of the class of which an entity should be created
299 */
300void NetworkGameManager::requestCreateEntity(ClassID classID)
301{
302  for ( int i = 0; i<outBuffer.size(); i++)
303  {
304    if ( !this->networkStream->isUserIdActive( i ) )
305      continue;
306
307    if ( !writeToClientBuffer( outBuffer[i], (byte)NET_REQUEST_CREATE ) )
308      return;
309    if ( !writeToClientBuffer( outBuffer[i], (int)classID ) )
310      return;
311  }
312}
313
314/*!
315 * Removes the specified entity on the server
316 * @param uniqueID: The ID of the entity object which should be removed
317 */
318void NetworkGameManager::requestRemoveEntity(int uniqueID)
319{
320  for ( int i = 0; i<outBuffer.size(); i++)
321  {
322    if ( !this->networkStream->isUserIdActive( i ) )
323      continue;
324
325    if ( !writeToClientBuffer( outBuffer[i], (byte)NET_REQUEST_REMOVE ) )
326      return;
327    if ( !writeToClientBuffer( outBuffer[i], uniqueID ) )
328      return;
329  }
330}
331
332/*!
333 * Creates the needed entity if possible
334 * This function is called if this is a server
335 * @param classID: The ID of the class of which an entity should be created
336 */
337int NetworkGameManager::executeCreateEntity(ClassID classID, int uniqueID, int owner)
338{
339  for ( int i = 0; i<outBuffer.size(); i++)
340  {
341    if ( !this->networkStream->isUserIdActive( i ) )
342      continue;
343
344    if ( !writeToClientBuffer( outBuffer[i], (byte)NET_CREATE_ENTITY ) )
345      return -1;
346    if ( !writeToClientBuffer( outBuffer[i], (int)classID ) )
347      return -1;
348    if ( !writeToClientBuffer( outBuffer[i], uniqueID ) )
349      return -1;
350    if ( !writeToClientBuffer( outBuffer[i], owner ) )
351      return -1;
352  }
353
354  PRINTF(0)("ExecuteCreateEntity: server side: classID: %x, uniqueID: %i, owner: %i\n", classID, uniqueID, owner);
355  doCreateEntity( classID, uniqueID, owner );
356
357  return uniqueID;
358}
359
360/*!
361 * Removes the specified entity
362 * This function is called if this is a server
363 * @param uniqueID: The ID of the entity object which should be removed
364 */
365void NetworkGameManager::executeRemoveEntity(int uniqueID)
366{
367  for ( int i = 0; i<outBuffer.size(); i++)
368  {
369    if ( !this->networkStream->isUserIdActive( i ) )
370      continue;
371
372    if ( !writeToClientBuffer( outBuffer[i], (byte)NET_REMOVE_ENTITY ) )
373      return;
374    if ( !writeToClientBuffer( outBuffer[i], uniqueID ) )
375      return;
376  }
377
378  doRemoveEntity(uniqueID);
379}
380
381/*!
382 * Checks whether it is possible to create an entity of a given class
383 * @return: true if the entity can be created, false otherwise
384 */
385bool NetworkGameManager::canCreateEntity(ClassID classID)
386{
387  return true;
388}
389
390/*!
391 * Sends the Entities to the new connected client
392 * @param userID: The ID of the user
393 */
394void NetworkGameManager::sendEntityList( int userID )
395{
396  if ( !isServer() )
397    return;
398
399  if ( userID >= outBuffer.size() )
400    resizeBufferVector( userID );
401
402  SynchronizeableList::const_iterator it, e;
403
404  it = this->networkStream->getSyncBegin();
405  e = this->networkStream->getSyncEnd();
406
407  // send the packet header
408  if ( !writeToClientBuffer( outBuffer[userID], (byte)NET_CREATE_ENTITY_LIST ) )
409    return;
410
411  // send the number of entities: -2 because you must not send network_game_manager and handshake
412  if ( !writeToClientBuffer( outBuffer[userID], networkStream->getSyncCount() ) )
413    return;
414
415  //PRINTF(0)("SendEntityList: n = %d\n", networkStream->getSyncCount()-2 );
416
417  // first send the NullParent
418  if ( !writeToClientBuffer( outBuffer[userID], (int)PNode::getNullParent()->getLeafClassID()) )
419    return;
420  if ( !writeToClientBuffer( outBuffer[userID], (int)PNode::getNullParent()->getUniqueID()) )
421    return;
422  if ( !writeToClientBuffer( outBuffer[userID], (int)PNode::getNullParent()->getOwner()) )
423    return;
424
425  // now send the rest of the entities
426  while ( it != e )
427  {
428    if( (*it)->beSynchronized() && (*it) != PNode::getNullParent())
429    {
430      PRINTF(0)("SENDING ENTITY %s classid: %x, uniqueid %d\n", (*it)->getClassName(), (*it)->getLeafClassID(), (*it)->getUniqueID() );
431      if ( !writeToClientBuffer( outBuffer[userID], (int)((*it)->getLeafClassID()) ) )
432        return;
433
434      if ( !writeToClientBuffer( outBuffer[userID], (int)((*it)->getUniqueID()) ) )
435        return;
436
437      if ( !writeToClientBuffer( outBuffer[userID], (int)((*it)->getOwner()) ) )
438        return;
439    }
440    it++;
441  }
442
443  signalNewPlayer( userID );
444}
445
446
447
448bool NetworkGameManager::signalNewPlayer(int userId)
449{
450  if ( userId >= outBuffer.size() )
451    resizeBufferVector( userId );
452
453  /* create new playable for Player*/
454  PRINTF(0)("Request for creation: %i\n", userId);
455  int uniqueId = this->createEntity(CL_SPACE_SHIP, userId);
456  PRINTF(0)("Request for creation: userid: %i, uniqueid: %i\n", userId, uniqueId);
457  this->sendYouAre(uniqueId, userId);
458
459}
460
461
462
463bool NetworkGameManager::signalLeftPlayer(int userID)
464{
465  const std::list<BaseObject*>* playableList = ClassList::getList(CL_PLAYABLE);
466  std::list<BaseObject*>::const_iterator it = playableList->begin();
467
468  for(; it != playableList->end(); it++)
469  {
470    if( dynamic_cast<Synchronizeable*>(*it)->getOwner() == userID )
471    {
472      PRINTF(0)("remove playable from %i\n", userID);
473      this->removeEntity(dynamic_cast<Synchronizeable*>(*it)->getUniqueID());
474      return true;
475    }
476  }
477  return false;
478}
479
480
481/**
482 * Creates a buffer for user n
483 * @param n The ID of the user
484 */
485void NetworkGameManager::resizeBufferVector( int n )
486{
487  for ( int i = outBuffer.size(); i<=n; i++)
488  {
489    clientBuffer outBuf;
490
491    outBuf.length = 0;
492
493    outBuf.maxLength = 5*1024;
494
495    outBuf.buffer = new byte[5*1014];
496
497    outBuffer.push_back(outBuf);
498  }
499}
500
501/**
502 * Creates the entity on this host
503 * @param classID: ClassID of the entity to create
504 * @param uniqueID: Unique ID to assign to the synchronizeable
505 * @param owner: owner of this synchronizealbe
506 */
507BaseObject* NetworkGameManager::doCreateEntity( ClassID classID, int uniqueID, int owner )
508{
509  PRINTF(0)("Creating Entity via Factory: classid: %x, uniqueID: %i, owner: %i\n", classID, uniqueID, owner);
510
511  BaseObject * b;
512  /* These are some small exeptions in creation: Not all objects can/should be created via Factory */
513  /* Exception 1: NullParent */
514  if( classID == CL_NULL_PARENT)
515  {
516    b = (BaseObject*)PNode::getNullParent();
517  }
518  else
519    b = Factory::fabricate( classID );
520
521  if ( !b )
522  {
523    PRINTF(1)("Could not fabricate Object with classID %x\n", classID);
524    return NULL;
525  }
526
527  if ( b->isA(CL_SYNCHRONIZEABLE) )
528  {
529    Synchronizeable * s = dynamic_cast<Synchronizeable*>(b);
530    s->setUniqueID( uniqueID );
531    s->setOwner( owner );
532    s->setSynchronized(true);
533    //this->networkStream->connectSynchronizeable( *s );
534    if ( !isServer() )
535      s->setIsOutOfSync( true );
536    PRINTF(0)("Fabricated %s with id %d\n", s->getClassName(), s->getUniqueID());
537
538    //TODO HACK: hack to prevent collision
539    if ( b->isA(CL_WORLD_ENTITY) && !b->isA(CL_PLAYABLE) )
540    {
541      if ( SharedNetworkData::getInstance()->getHostID()!=0 )
542      {
543        static Vector pos = Vector(1000.0, 1000.0, 1000.0);
544        PNode *p = dynamic_cast<PNode*>(b);
545        p->setAbsCoor(pos);
546        p->updateNode(0);
547        pos += Vector(1000.0, 1000.0, 1000.0);
548      }
549    }
550    ///TODO HACK this is only for network multiplayer games.
551    if( b->isA(CL_PLAYABLE))
552    {
553      Playable* ss = dynamic_cast<Playable*>(b);
554      if( owner%2 == 0)
555      {
556
557        ss->loadModel("models/ships/reap_0.obj");
558        ss->toList(OM_GROUP_00);
559        ss->setAbsCoor(213.37, 57.71, -47.98);
560        ss->setAbsDir(Quaternion(0.16, 0.98, -0.10));
561      }
562      else
563      {
564        ss->loadModel( "models/ships/fighter.obj" );
565        ss->toList(OM_GROUP_01);
566        ss->setAbsCoor(-314.450, 40.701, 83.554);
567      }
568    }
569
570    return b;
571  }
572  else
573  {
574    PRINTF(1)("Class with ID %x is not a synchronizeable!", (int)classID);
575    delete b;
576  }
577  return NULL;
578}
579
580/**
581 * Removes a entity on this host
582 * @param uniqueID: unique ID assigned with the entity to remove
583 */
584void NetworkGameManager::doRemoveEntity( int uniqueID )
585{
586  SynchronizeableList::const_iterator it,e;
587  it = this->networkStream->getSyncBegin();
588  e = this->networkStream->getSyncEnd();
589
590  while ( it != e )
591  {
592    if ( (*it)->getUniqueID() == uniqueID )
593    {
594      assert((*it)->isA(CL_WORLD_ENTITY));
595      dynamic_cast<WorldEntity*>(*it)->leaveWorld();
596      dynamic_cast<WorldEntity*>(*it)->toList(OM_DEAD);
597      break;
598    }
599    it++;
600  }
601}
602
603/**
604 * Tell the synchronizeable that a user's synchronizeable is out of sync
605 * @param uniqueID: unique ID assigned with the entity which is out of sync
606 * @param userID: user ID who's synchronizeable is out of sync
607 */
608void NetworkGameManager::doRequestSync( int uniqueID, int userID )
609{
610  SynchronizeableList::const_iterator it,e;
611  it = this->networkStream->getSyncBegin();
612  e = this->networkStream->getSyncEnd();
613
614  while ( it != e )
615  {
616    if ( (*it)->getUniqueID() == uniqueID )
617    {
618      (*it)->requestSync( userID );
619      break;
620    }
621    it++;
622  }
623}
624
625/**
626 * Copies length bytes to the clientBuffer with error checking
627 * @param clientBuffer: the clientBuffer to write to
628 * @param data: buffer to the data
629 * @param length: length of data
630 * @return false on error true else
631 */
632bool NetworkGameManager::writeToClientBuffer( clientBuffer &cb, byte * data, int length )
633{
634  if ( length > cb.maxLength-cb.length )
635  {
636    PRINTF(1)("No space left in clientBuffer\n");
637    return false;
638  }
639
640  memcpy( cb.buffer+cb.length, data, length );
641  return true;
642}
643
644/**
645 * Reads data from clientBuffer with error checking
646 * @param clientBuffer: the clientBuffer to read from
647 * @param data: pointer to the buffer
648 * @param length:
649 * @return
650 */
651bool NetworkGameManager::readFromClientBuffer( clientBuffer &cb, byte * data, int length )
652{
653  if ( cb.length < length )
654  {
655    PRINTF(0)("There is not enough data in clientBuffer\n");
656    return 0;
657  }
658
659  memcpy( data, cb.buffer+cb.length-length, length );
660  return true;
661}
662
663/**
664 * Tells this client that he has to control this entity
665 * @param uniqueID: the entity's uniqeID
666 */
667void NetworkGameManager::doYouAre( int uniqueID )
668{
669
670  SynchronizeableList::const_iterator it = this->networkStream->getSyncBegin();
671
672  Playable *p = NULL;
673  Synchronizeable *s = NULL;
674
675  for ( ; it !=networkStream->getSyncEnd(); it++ )
676  {
677    if ( (*it)->getUniqueID()==uniqueID )
678    {
679      if ( (*it)->isA( CL_SYNCHRONIZEABLE ) )
680      {
681        s = dynamic_cast<Synchronizeable*>(*it);
682      }
683      if ( (*it)->isA( CL_PLAYABLE ) )
684      {
685        p = dynamic_cast<Playable*>(*it);
686        break;
687      } else
688      {
689        PRINTF(1)("UniqueID is not a Playable\n");
690      }
691    }
692  }
693
694  Player* player = State::getPlayer();
695  assert(p != NULL);
696  assert(s != NULL);
697  assert(player != NULL);
698
699  s->setIsOutOfSync( true );
700
701  PRINTF(0)("uniqueID = %d\n", s->getUniqueID());
702
703  player->setPlayable(p);
704
705
706}
707
708/**
709 * Tells a remote client that he has to control this entity
710 * @param uniqueID: the entity's uniqeID
711 * @param userID: the users ID
712 */
713void NetworkGameManager::sendYouAre( int uniqueID, int userID )
714{
715  if ( !isServer() )
716    return;
717
718  if ( userID != 0 )
719  {
720    if ( !writeToClientBuffer( outBuffer[userID], (byte)NET_YOU_ARE_ENTITY ) )
721      return;
722
723    if ( !writeToClientBuffer( outBuffer[userID], uniqueID ) )
724      return;
725  }
726  else
727  {
728    doYouAre(uniqueID);
729  }
730}
731
732bool NetworkGameManager::handleRequestCreate( int & i, const byte * data, int length, int sender )
733{
734  if ( INTSIZE > length-i )
735  {
736    PRINTF(1)("Cannot read classID from buffer! Not enough data left!\n");
737    return false;
738  }
739  int classID;
740  i += Converter::byteArrayToInt( &data[i], &classID );
741
742  createEntity( (ClassID)classID );
743
744  return true;
745}
746
747bool NetworkGameManager::handleRequestRemove( int & i, const byte * data, int length, int sender )
748{
749  if ( INTSIZE > length-i )
750  {
751    PRINTF(1)("Cannot read uniqueID from buffer! Not enough data left!\n");
752    return false;
753  }
754  int uniqueID;
755  i += Converter::byteArrayToInt( &data[i], &uniqueID );
756
757  removeEntity( uniqueID );
758
759  return true;
760}
761
762bool NetworkGameManager::handleCreateEntity( int & i, const byte * data, int length, int sender )
763{
764  if ( INTSIZE > length-i )
765  {
766    PRINTF(1)("Cannot read classID from buffer! Not enough data left!\n");
767    return false;
768  }
769  int classID;
770  i += Converter::byteArrayToInt( &data[i], &classID );
771
772  if ( INTSIZE > length-i )
773  {
774    PRINTF(1)("Cannot read uniqueID from buffer! Not enough data left!\n");
775    return false;
776  }
777  int uniqueID;
778  i += Converter::byteArrayToInt( &data[i], &uniqueID );
779
780  if ( INTSIZE > length-i )
781  {
782    PRINTF(1)("Cannot read owner from buffer! Not enough data left!\n");
783    return false;
784  }
785  int owner;
786  i += Converter::byteArrayToInt( &data[i], &owner );
787
788  PRINTF(0)("handleCreateEntity: client side: classID: %x, uniqueID: %i, owner: %i\n", classID, uniqueID, owner);
789  doCreateEntity( (ClassID)classID, uniqueID, owner );
790
791  return true;
792}
793
794bool NetworkGameManager::handleRemoveEntity( int & i, const byte * data, int length, int sender )
795{
796  if ( INTSIZE > length-i )
797  {
798    PRINTF(1)("Cannot read uniqueID from buffer! Not enough data left!\n");
799    return false;
800  }
801  int uniqueID;
802  i += Converter::byteArrayToInt( &data[i], &uniqueID );
803
804  doRemoveEntity( uniqueID );
805
806  return true;
807}
808
809bool NetworkGameManager::handleCreateEntityList( int & i, const byte * data, int length, int sender )
810{
811  if ( INTSIZE > length-i )
812  {
813    PRINTF(1)("Cannot read n from buffer! Not enough data left!\n");
814    return false;
815  }
816
817  PRINTF(0)("HandleCreateEntityList:  data[i..i+3] = %d %d %d %d\n", data[i], data[i+1], data[i+2], data[i+3]);
818
819  int n;
820  i += Converter::byteArrayToInt( &data[i], &n );
821
822
823  PRINTF(0)("HandleCreateEntityList: n = %d\n", n);
824
825  int classID, uniqueID, owner;
826
827  for ( int j = 0; j<n; j++ )
828  {
829
830    if ( INTSIZE > length-i )
831    {
832      PRINTF(1)("Cannot read classID from buffer! Not enough data left!\n");
833      return false;
834    }
835    i += Converter::byteArrayToInt( &data[i], &classID );
836
837    if ( INTSIZE > length-i )
838    {
839      PRINTF(1)("Cannot read uniqueID from buffer! Not enough data left!\n");
840      return false;
841    }
842    i += Converter::byteArrayToInt( &data[i], &uniqueID );
843
844    if ( INTSIZE > length-i )
845    {
846      PRINTF(1)("Cannot read owner from buffer! Not enough data left!\n");
847      return false;
848    }
849    i += Converter::byteArrayToInt( &data[i], &owner );
850
851    if ( classID != CL_NETWORK_GAME_MANAGER && classID != CL_HANDSHAKE )
852    {
853      BaseObject* b = doCreateEntity( (ClassID)classID, uniqueID, owner );
854    }
855
856  }
857
858  return true;
859}
860
861bool NetworkGameManager::handleRemoveEntityList( int & i, const byte * data, int length, int sender )
862{
863  if ( INTSIZE > length-i )
864  {
865    PRINTF(1)("Cannot read n from buffer! Not enough data left!\n");
866    return false;
867  }
868  int n;
869  i += Converter::byteArrayToInt( &data[i], &n );
870
871  int uniqueID;
872
873  for ( int j = 0; j<n; j++ )
874  {
875
876    if ( INTSIZE > length-i )
877    {
878      PRINTF(1)("Cannot read uniqueID from buffer! Not enough data left!\n");
879      return false;
880    }
881    i += Converter::byteArrayToInt( &data[i], &uniqueID );
882
883    doRemoveEntity( uniqueID );
884  }
885
886  return true;
887}
888
889bool NetworkGameManager::handleYouAreEntity( int & i, const byte * data, int length, int sender )
890{
891  if ( INTSIZE > length-i )
892  {
893    PRINTF(1)("Cannot read uniqueID from buffer! Not enough data left!\n");
894    return false;
895  }
896
897  int uniqueID;
898  i += Converter::byteArrayToInt( &data[i], &uniqueID );
899
900  doYouAre( uniqueID );
901
902  return true;
903}
904
905bool NetworkGameManager::handleRequestSync( int & i, const byte * data, int length, int sender )
906{
907  if ( INTSIZE > length-i )
908  {
909    PRINTF(1)("Cannot read uniqueID from buffer! Not enough data left!\n");
910    return false;
911  }
912  int uniqueID;
913  i += Converter::byteArrayToInt( &data[i], &uniqueID );
914
915  PRINTF(0)("handleRequestSync %d %d\n", uniqueID, sender);
916  doRequestSync( uniqueID, sender );
917
918  return true;
919}
920
921
922/**
923 *  handles the network signal NET_REQUEST_PNODE_PATH
924 * @param i byte offset in the buffer
925 * @param data data array
926 * @param length length of the data arary
927 * @param sender the sender id
928 * @return true if process terminated sucessfully
929 */
930bool NetworkGameManager::handleRequestPNodePath(int& i, const byte* data, int length, int sender)
931{
932  if( INTSIZE > length-i )
933  {
934    PRINTF(1)("Cannot read n from buffer! Not enough data left!\n");
935    return false;
936  }
937  PRINTF(0)("HandleRequestPNodePath:  data[i..i+3] = %d %d %d %d\n", data[i], data[i+1], data[i+2], data[i+3]);
938
939  int uniqueID1, uniqueID2;
940  if( INTSIZE > length-i )
941  {
942    PRINTF(1)("Cannot read uniqueID from buffer! Not enough data left!\n");
943    return false;
944  }
945  i += Converter::byteArrayToInt( &data[i], &uniqueID1 );
946
947  if( INTSIZE > length-i )
948  {
949    PRINTF(1)("Cannot read uniqueID from buffer! Not enough data left!\n");
950    return false;
951  }
952  i += Converter::byteArrayToInt( &data[i], &uniqueID2 );
953
954
955  PRINTF(0)("HandleRequestPNodePath: got a request for path from uid %i to uid %i\n", uniqueID1, uniqueID2);
956
957  return true;
958}
959
960
961bool NetworkGameManager::writeToClientBuffer( clientBuffer & cb, byte b )
962{
963  if ( cb.maxLength-cb.length < 1 )
964  {
965    PRINTF(1)("Cannot write to clientBuffer! Not enough space for 1 byte\n");
966    return false;
967  }
968
969  cb.buffer[cb.length++] = b;
970
971  return true;
972}
973
974bool NetworkGameManager::writeToClientBuffer( clientBuffer & cb, int i )
975{
976  int n = Converter::intToByteArray( i, cb.buffer+cb.length, cb.maxLength-cb.length );
977  cb.length += n;
978
979  if ( n <= 0 )
980  {
981    PRINTF(1)("Cannot write to clientBuffer! Not enough space for 1 int\n");
982    return false;
983  }
984
985  return true;
986}
987
988void NetworkGameManager::sync( int uniqueID, int owner )
989{
990  /*if ( owner==this->getHostID() )
991  return;*/
992
993  if ( !isServer() )
994    executeRequestSync( uniqueID, 0 );
995  else
996    executeRequestSync( uniqueID, owner );
997}
998
999void NetworkGameManager::executeRequestSync( int uniqueID, int user )
1000{
1001  PRINTF(0)("executeRequestSync %d %d\n", uniqueID, user);
1002  if ( user >= outBuffer.size() )
1003    resizeBufferVector( user );
1004
1005  if ( !writeToClientBuffer( outBuffer[user], (byte)NET_REQUEST_SYNC ) )
1006    return;
1007  if ( !writeToClientBuffer( outBuffer[user], uniqueID ) )
1008    return;
1009}
1010
Note: See TracBrowser for help on using the repository browser.