Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/netp6/src/network/packet/FunctionCalls.cc @ 3607

Last change on this file since 3607 was 3214, checked in by scheusso, 16 years ago

merged netp5 back to trunk

  • Property svn:eol-style set to native
File size: 9.3 KB
Line 
1/*
2 *   ORXONOX - the hottest 3D action shooter ever to exist
3 *                    > www.orxonox.net <
4 *
5 *
6 *   License notice:
7 *
8 *   This program is free software; you can redistribute it and/or
9 *   modify it under the terms of the GNU General Public License
10 *   as published by the Free Software Foundation; either version 2
11 *   of the License, or (at your option) any later version.
12 *
13 *   This program is distributed in the hope that it will be useful,
14 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
15 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 *   GNU General Public License for more details.
17 *
18 *   You should have received a copy of the GNU General Public License
19 *   along with this program; if not, write to the Free Software
20 *   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
21 *
22 *   Author:
23 *      Oliver Scheuss <scheusso [at] ee.ethz.ch>, (C) 2008
24 *   Co-authors:
25 *      ...
26 *
27 */
28
29#include "FunctionCalls.h"
30
31#include <cassert>
32#include <cstring>
33#include "util/MultiType.h"
34#include "network/NetworkFunction.h"
35
36namespace orxonox {
37namespace packet {
38 
39#define   PACKET_FLAGS_FUNCTIONCALLS PacketFlag::Reliable
40#define   _PACKETID         0
41const unsigned int FUNCTIONCALLS_MEM_ALLOCATION = 1000;
42   
43FunctionCalls::FunctionCalls()
44 : Packet()
45{
46  flags_ = flags_ | PACKET_FLAGS_FUNCTIONCALLS;
47  currentSize_ = 2*sizeof(uint32_t); // for packetid and nrOfCalls
48  nrOfCalls_ = 0;
49  currentMemBlocks_ = 1;
50  data_=new uint8_t[ FUNCTIONCALLS_MEM_ALLOCATION ];
51  *(ENUM::Type *)(data_ + _PACKETID ) = ENUM::FunctionCalls;
52  *(uint32_t*)(data_+sizeof(uint32_t)) = 0; // set nrOfCalls to 0
53}
54
55FunctionCalls::FunctionCalls( uint8_t* data, unsigned int clientID )
56  : Packet(data, clientID)
57{
58}
59
60FunctionCalls::~FunctionCalls()
61{
62}
63
64
65bool FunctionCalls::process(){
66  assert(isDataENetAllocated());
67  uint8_t* temp = data_+sizeof(uint32_t); //skip packetid
68  this->nrOfCalls_ = *(uint32_t*)temp;
69  temp += sizeof(uint32_t);
70  for( unsigned int i = 0; i<this->nrOfCalls_; i++ )
71  {
72    uint32_t functionID = *(uint32_t*)temp;
73    bool isStatic = *(uint8_t*)(temp+sizeof(uint32_t));
74    if( isStatic )
75    {
76      MultiType mt1, mt2, mt3, mt4, mt5;
77      NetworkFunctionStatic *fct = NetworkFunctionStatic::getFunction( functionID );
78      uint32_t nrOfArguments = *(uint32_t*)(temp+sizeof(uint32_t)+sizeof(uint8_t));
79      temp+=2*sizeof(uint32_t)+sizeof(uint8_t);
80      switch(nrOfArguments)
81      {
82        case 0:
83          fct->call();
84          break;
85        case 1:
86          mt1.importData(temp);
87          fct->call(mt1);
88          break;
89        case 2:
90          mt1.importData(temp);
91          mt2.importData(temp);
92          fct->call(mt1, mt2);
93          break;
94        case 3:
95          mt1.importData(temp);
96          mt2.importData(temp);
97          mt3.importData(temp);
98          fct->call(mt1, mt2, mt3);
99          break;
100        case 4:
101          mt1.importData(temp);
102          mt2.importData(temp);
103          mt3.importData(temp);
104          mt4.importData(temp);
105          fct->call(mt1, mt2, mt3, mt4);
106          break;
107        case 5:
108          mt1.importData(temp);
109          mt2.importData(temp);
110          mt3.importData(temp);
111          mt4.importData(temp);
112          mt5.importData(temp);
113          fct->call(mt1, mt2, mt3, mt4, mt5);
114          break;
115        default:
116          assert(0);
117      }
118    }
119    else // not a static function, so also handle the objectID
120    {
121      MultiType mt1, mt2, mt3, mt4, mt5;
122      NetworkMemberFunctionBase *fct = NetworkMemberFunctionBase::getFunction( functionID );
123      uint32_t nrOfArguments = *(uint32_t*)(temp+sizeof(uint32_t)+sizeof(uint8_t));
124      uint32_t objectID = *(uint32_t*)(temp+2*sizeof(uint32_t)+sizeof(uint8_t));
125      temp+=3*sizeof(uint32_t)+sizeof(uint8_t);
126      switch(nrOfArguments)
127      {
128        case 0:
129          fct->call(objectID);
130          break;
131        case 1:
132          mt1.importData(temp);
133          fct->call(objectID, mt1);
134          break;
135        case 2:
136          mt1.importData(temp);
137          mt2.importData(temp);
138          fct->call(objectID, mt1, mt2);
139          break;
140        case 3:
141          mt1.importData(temp);
142          mt2.importData(temp);
143          mt3.importData(temp);
144          fct->call(objectID, mt1, mt2, mt3);
145          break;
146        case 4:
147          mt1.importData(temp);
148          mt2.importData(temp);
149          mt3.importData(temp);
150          mt4.importData(temp);
151          fct->call(objectID, mt1, mt2, mt3, mt4);
152          break;
153        case 5:
154          mt1.importData(temp);
155          mt2.importData(temp);
156          mt3.importData(temp);
157          mt4.importData(temp);
158          mt5.importData(temp);
159          fct->call(objectID, mt1, mt2, mt3, mt4, mt5);
160          break;
161        default:
162          assert(0);
163          break;
164      }
165    }
166  }
167  delete this;
168  return true;
169}
170
171void FunctionCalls::addCallStatic( uint32_t networkID, const MultiType* mt1, const MultiType* mt2, const MultiType* mt3, const MultiType* mt4, const MultiType* mt5){
172  assert(!isDataENetAllocated());
173 
174  // first determine the size that has to be reserved for this call
175  uint32_t callsize = 2*sizeof(uint32_t)+sizeof(uint8_t); //size for network-function-id and nrOfArguments and for bool isStatic
176  uint32_t nrOfArguments = 0;
177  if(mt1)
178  {
179    nrOfArguments++;
180    callsize += mt1->getNetworkSize();
181    if(mt2)
182    {
183      nrOfArguments++;
184      callsize += mt2->getNetworkSize();
185      if(mt3)
186      {
187        nrOfArguments++;
188        callsize += mt3->getNetworkSize();
189        if(mt4)
190        {
191          nrOfArguments++;
192          callsize += mt4->getNetworkSize();
193          if(mt5)
194          {
195            nrOfArguments++;
196            callsize += mt5->getNetworkSize();
197          }
198        }
199      }
200    }
201  }
202 
203  // now allocated mem if neccessary
204  if( currentSize_ + callsize > currentMemBlocks_*FUNCTIONCALLS_MEM_ALLOCATION )
205  {
206    currentMemBlocks_ = (currentSize_ + callsize)%FUNCTIONCALLS_MEM_ALLOCATION+1;
207    uint8_t *temp = new uint8_t[currentMemBlocks_*FUNCTIONCALLS_MEM_ALLOCATION];
208    memcpy( temp, data_, currentSize_ );
209    delete[] data_;
210    data_ = temp;
211  }
212 
213  // now serialise the mt values and copy the function id and isStatic
214  uint8_t* temp = data_+currentSize_;
215  *(uint32_t*)(data_+sizeof(uint32_t)) = *(uint32_t*)(data_+sizeof(uint32_t))+1; // increase number of calls
216  *(uint32_t*)temp = networkID;
217  *(uint8_t*)(temp+sizeof(uint32_t)) = true;
218  *(uint32_t*)(temp+sizeof(uint32_t)+sizeof(uint8_t)) = nrOfArguments;
219  temp += 2*sizeof(uint32_t)+sizeof(uint8_t);
220  if(mt1)
221  {
222    mt1->exportData( temp ); //temp gets automatically increased
223    if(mt2)
224    {
225      mt2->exportData( temp ); //temp gets automatically increased
226      if(mt3)
227      {
228        mt3->exportData( temp ); //temp gets automatically increased
229        if(mt4)
230        {
231          mt4->exportData( temp ); //temp gets automatically increased
232          if(mt5)
233          {
234            mt5->exportData( temp ); //temp gets automatically increased
235          }
236        }
237      }
238    }
239  }
240  //currentSize_ += callsize;
241  currentSize_ = temp-data_;
242 
243}
244
245void FunctionCalls::addCallMember( uint32_t networkID, uint32_t objectID, const MultiType* mt1, const MultiType* mt2, const MultiType* mt3, const MultiType* mt4, const MultiType* mt5){
246  assert(!isDataENetAllocated());
247 
248  // first determine the size that has to be reserved for this call
249  uint32_t callsize = 3*sizeof(uint32_t)+sizeof(uint8_t); //size for network-function-id and nrOfArguments and the objectID
250  uint32_t nrOfArguments = 0;
251  if(mt1)
252  {
253    nrOfArguments++;
254    callsize += mt1->getNetworkSize();
255    if(mt2)
256    {
257      nrOfArguments++;
258      callsize += mt2->getNetworkSize();
259      if(mt3)
260      {
261        nrOfArguments++;
262        callsize += mt3->getNetworkSize();
263        if(mt4)
264        {
265          nrOfArguments++;
266          callsize += mt4->getNetworkSize();
267          if(mt5)
268          {
269            nrOfArguments++;
270            callsize += mt5->getNetworkSize();
271          }
272        }
273      }
274    }
275  }
276 
277  // now allocated mem if neccessary
278  if( currentSize_ + callsize > currentMemBlocks_*FUNCTIONCALLS_MEM_ALLOCATION )
279  {
280    currentMemBlocks_ = (currentSize_ + callsize)%FUNCTIONCALLS_MEM_ALLOCATION+1;
281    uint8_t *temp = new uint8_t[currentMemBlocks_*FUNCTIONCALLS_MEM_ALLOCATION];
282    memcpy( temp, data_, currentSize_ );
283    delete[] data_;
284    data_ = temp;
285  }
286 
287  // now serialise the mt values and copy the function id
288  uint8_t* temp = data_+currentSize_;
289  *(uint32_t*)(data_+sizeof(uint32_t)) = *(uint32_t*)(data_+sizeof(uint32_t))+1; // increase number of calls
290  *(uint32_t*)temp = networkID;
291  *(uint8_t*)(temp+sizeof(uint32_t)) = false;
292  *(uint32_t*)(temp+sizeof(uint32_t)+sizeof(uint8_t)) = nrOfArguments;
293  *(uint32_t*)(temp+2*sizeof(uint32_t)+sizeof(uint8_t)) = objectID;
294  temp += 3*sizeof(uint32_t)+sizeof(uint8_t);
295  if(mt1)
296  {
297    mt1->exportData( temp ); //temp gets automatically increased
298    if(mt2)
299    {
300      mt2->exportData( temp ); //temp gets automatically increased
301      if(mt3)
302      {
303        mt3->exportData( temp ); //temp gets automatically increased
304        if(mt4)
305        {
306          mt4->exportData( temp ); //temp gets automatically increased
307          if(mt5)
308          {
309            mt5->exportData( temp ); //temp gets automatically increased
310          }
311        }
312      }
313    }
314  }
315  currentSize_ += callsize;
316 
317}
318
319
320} //namespace packet
321} //namespace orxonox
Note: See TracBrowser for help on using the repository browser.