CTR Pia  4.11.3
Game Communication Engine
clone_EventCloneElementBase.h
1 /*---------------------------------------------------------------------------*
2  Project: Pia
3  File: clone_EventCloneElementBase.h
4 
5  Copyright Nintendo. All rights reserved.
6 
7  These coded instructions, statements, and computer programs contain
8  proprietary information of Nintendo of America Inc. and/or Nintendo
9  Company Ltd., and are protected by Federal copyright law. They may
10  not be disclosed to third parties or copied or duplicated in any form,
11  in whole or in part, without the prior written consent of Nintendo.
12  *---------------------------------------------------------------------------*/
13 
14 
15 #pragma once
16 
17 #include <pia/clone/clone_definitions.h>
18 #include <pia/clone/clone_CloneElementBase.h>
19 #include <pia/common/common_OffsetList.h>
20 
21 namespace nn
22 {
23 namespace pia
24 {
25 namespace clone
26 {
27 
28 class IDataPacker;
29 
30 /*!
31 @brief This is the base class for managing the sending and receiving of events.
32 
33 @date 2014-06-03 Fixed a bug where if the first sent event was dropped, the second event or later events were treated as the first event.
34 @date 2014-03-12 Added a function that gets the current number of event buffers in use.
35 @date 2013-07-18 Initial version.
36 */
38 {
39 public:
40 /*!
41 @brief Destroys the object.
42 */
43  virtual ~EventCloneElementBase();
44 
45 
46 /*!
47 @brief Prints information that is useful for debugging.
48 
49 @param[in] flag Specifies the bitwise OR of trace flags. For more information, see the <tt>@ref TraceFlag</tt> type.
50 */
51  void Trace(u64 flag) const;
52 
53 
54 /*!
55 @brief Gets whether a drop event error occurred.
56 @details If a station disconnects abnormally when using <tt>AtomicSharingClone</tt>, an event that was supposed to be received may be lost.
57 If this error occurs in any of the <tt>EventCloneElement</tt> objects, the <tt>CloneProtocol::GetError</tt> function returns <tt>CloneProtocol::ERROR_TYPE_DROP_EVENT</tt>.
58 @return Returns <tt>true</tt> if a drop event error occurred.
59 @see CloneProtocol::GetError
60 
61 
62 */
63  bool IsDropEvent() const
64  {
65  return m_IsDropEvent;
66  }
67 
68 /*!
69 @brief Gets the current number of event buffers in use.
70 
71 @details Sometimes the return value is not zero (0) when it is registered to <tt>ReceiveClone</tt>, <tt>AtomicSharingClone</tt>, or <tt>SequentialSharingClone</tt>.
72 When subsequent data is received, data that can be deleted will be deleted from the buffer.
73 
74 @return Returns the number of event buffers in use.
75 
76 */
77  size_t GetUsingBufferNum() const;
78 
79 
80 /*!
81 @cond PRIVATE
82 @brief Gets the station from which the event, specified within the event buffer, is waiting for an Ack.
83 
84 @param[in] index The index of the target event, when the earliest event in the event buffer has an index of 0.
85 Set a value equal or larger than 0 and less than the number of events used by the buffer currently.
86 
87 @return Returns a bitmap that indicates the station index for the station from which the specified event is waiting for an Ack.
88 @see GetUsingBufferNum
89 */
90  u32 GetBufferEventWaitingStationIndexBitmap(int index) const;
91  //! @endcond
92 
93 /*!
94 @cond PRIVATE
95 @brief Gets the clock value for the event specified within the event buffer.
96 
97 @param[in] index The index of the target event, when the earliest event in the event buffer has an index of 0.
98 Set a value equal or larger than 0 and less than the number of events used by the buffer currently.
99 
100 @return Returns a clock value for the specified event. Returns <tt>0</tt> when no event is targeted.
101 @see GetUsingBufferNum
102 */
103  ClockValue GetBufferEventClock(int index) const;
104  //! @endcond
105 
106 
107  //! @cond PRIVATE
108 
109 public:
110  virtual u16 GetType() const
111  {
112  return GetTypeStatic();
113  }
114  virtual bool IsSupportedClone(int cloneType) const;
115 
116  static u16 GetTypeStatic()
117  {
118  return TYPE_EVENT;
119  }
120 
121  static bool Receive(
122  CloneElementBase* pElement,
123  IDataPacker* pAckPacker,
124  const void* cpChunk,
125  u16 chunkSize,
126  Id elementId,
127  StationIndex src,
128  StationIndex localStationIndex,
129  u32 dispatchCount);
130 
131  static size_t GetDataChunkHeaderSize();
132 
133 public:
134  typedef u16 Index;
135 
136 private:
137  enum ReceiveDataResponse
138  {
139  RESPONSE_NOTHING,
140  RESPONSE_ACK,
141  RESPONSE_PRESERVER_MIGRATION
142  };
143  ReceiveDataResponse ReceiveData(const void* cpData, size_t size, StationIndex src, StationIndex setter, ClockValue clock, u64 registerCountAll, u32 destBitmap, Index index, Index eraseIndex);
144  void ReceiveAck(StationIndex src, Index index);
145  void ReceivePreserverMigration(StationIndex src, Index index);
146 
147  void ReceiveInitial(StationIndex src, Index index);
148  void ReceiveInitialAck(StationIndex src);
149 
150 public:
151  virtual void ClearData();
152 
153  virtual void RemoveDest(StationIndex stationId);
154  virtual void AddParticipant(StationIndex stationId);
155  virtual void Complement(StationIndex stationId);
156  virtual void Lock();
157 
158 protected:
159  static const size_t cBufferSizeMin = 2;
160  static const size_t cBufferSizeMax = 0x3fff;
161 
162 public:
163  class EventSendToken : public CloneElementBase::ResendableSendToken
164  {
165  public:
166  enum TokenType
167  {
168  TOKEN_INITIAL,
169  TOKEN_EVENT
170  };
171  virtual TokenType GetTokenType() const = 0;
172  };
173 
174 
175  class EventInitialToken : public EventSendToken
176  {
177  public:
178  explicit EventInitialToken(EventCloneElementBase* pElement)
179  : EventSendToken(), m_pElement(pElement)
180  {
181  }
182 
183  virtual Type GetElementType() const
184  {
185  return TYPE_EVENT;
186  }
187  virtual u32 GetDestBitmap() const
188  {
189  return m_DestBitmap;
190  }
191  virtual TokenType GetTokenType() const
192  {
193  return TOKEN_INITIAL;
194  }
195  virtual size_t GetChunkSize() const;
196  virtual void WriteChunk(void* pChunkBuffer) const;
197  virtual CloneElementBase* GetElement()
198  {
199  return m_pElement;
200  }
201 
202  Id GetId() const
203  {
204  return m_pElement->GetId();
205  }
206 
207  Index GetInitialIndex() const
208  {
209  return m_pElement->m_pEventTokenBuffer->GetNextIndex();
210  }
211  void SetDestBitmap(u32 destBitmap)
212  {
213  m_DestBitmap = destBitmap;
214  }
215 
216  private:
217  EventCloneElementBase* m_pElement;
218  u32 m_DestBitmap;
219  };
220 
221 
222  class EventTokenBase : public EventSendToken
223  {
224  public:
225  EventTokenBase()
226  : EventSendToken()
227  {
228  }
229  void Init(EventCloneElementBase* pElement)
230  {
231  m_pElement = pElement;
232  }
233 
234  virtual Type GetElementType() const
235  {
236  return TYPE_EVENT;
237  }
238  virtual u32 GetDestBitmap() const
239  {
240  return m_DestBitmap;
241  }
242  virtual TokenType GetTokenType() const
243  {
244  return TOKEN_EVENT;
245  }
246  virtual size_t GetChunkSize() const;
247  virtual void WriteChunk(void* pChunkBuffer) const;
248  virtual CloneElementBase* GetElement()
249  {
250  return m_pElement;
251  }
252  virtual bool IsUnicast() const
253  {
254  return true;
255  }
256 
257  Index GetIndex() const
258  {
259  return m_Index;
260  }
261  StationIndex GetSetterStationIndex() const
262  {
263  return m_SetterStationIndex;
264  }
265  StationIndex GetPreserverStationIndex() const
266  {
267  return m_PreserverStationIndex;
268  }
269  const ClockValue& GetClock() const
270  {
271  return m_Clock;
272  }
273  u64 GetRegisterCountAll() const
274  {
275  return m_RegisterCountAll;
276  }
277 
278  void SetDestBitmap(u32 destBitmap)
279  {
280  m_DestBitmap = destBitmap;
281  }
282  void RemoveDestBmp(u32 bmp)
283  {
284  m_DestBitmap &= ~bmp;
285  }
286  void RemoveDestAll()
287  {
288  m_DestBitmap = 0;
289  }
290  void SetIndex(Index index)
291  {
292  m_Index = index;
293  }
294  void SetSetterStationIndex(StationIndex stationId)
295  {
296  m_SetterStationIndex = stationId;
297  }
298  void SetPreserverStationIndex(StationIndex stationId)
299  {
300  m_PreserverStationIndex = stationId;
301  }
302  void SetClock(ClockValue clock)
303  {
304  m_Clock = clock;
305  }
306  void SetRegisterCountAll(u64 count)
307  {
308  m_RegisterCountAll = count;
309  }
310 
311  enum State
312  {
313  EVENT_TOKEN_STATE_EMPTY,
314  EVENT_TOKEN_STATE_SET,
315  EVENT_TOKEN_STATE_RECEIVED,
316  EVENT_TOKEN_STATE_HANDLED
317  };
318 
319  State GetState() const
320  {
321  return m_State;
322  }
323  void SetState(State state)
324  {
325  m_State = state;
326  }
327 
328  Id GetId() const
329  {
330  return m_pElement->GetId();
331  }
332  virtual size_t GetSize() const
333  {
334  return m_pElement->GetSize();
335  }
336  virtual void Serialize(void* pBuffer) const = 0;
337  virtual void Deserialize(const void* cpBuffer) = 0;
338  Index GetEraseIndex() const
339  {
340  return m_pElement->m_pEventTokenBuffer->GetEraseIndex();
341  }
342 
343  void CancelSendData()
344  {
345  m_pElement->CancelSendData(this);
346  }
347  void AddSendData()
348  {
349  m_pElement->AddSendData(this);
350  }
351 
352  private:
353  EventCloneElementBase* m_pElement;
354  u32 m_DestBitmap;
355  Index m_Index;
356  StationIndex m_SetterStationIndex;
357  StationIndex m_PreserverStationIndex;
358  ClockValue m_Clock;
359  u64 m_RegisterCountAll;
360  State m_State;
361  };
362 
363 
364  class EventTokenBufferBase
365  {
366  protected:
367  explicit EventTokenBufferBase(u32 size);
368 
369  public:
370  void Clear();
371  void InitIndex(Index index);
372  EventTokenBase* Get(Index index);
373  EventTokenBase* AssignNext();
374  EventTokenBase* Assign(Index index);
375  void Recycle();
376  bool ShiftHead();
377  Index GetHeadIndex() const
378  {
379  return At(m_HeadIdx)->GetIndex();
380  }
381  bool IsEmpty() const
382  {
383  return (m_Num == 0);
384  }
385  Index GetEraseIndex() const
386  {
387  return m_EraseIndex;
388  }
389  Index GetNextIndex() const;
390 
391  void RemoveDest(StationIndex stationId);
392  void Complement(StationIndex stationId, u32 destBitmap);
393  void Lock();
394 
395  size_t GetUsingBufferNum()
396  {
397  return m_Num;
398  }
399 
400  u32 GetBufferEventWaitingStationIndexBitmap(int index) const;
401  ClockValue GetBufferEventClock(int index) const;
402 
403  protected:
404  virtual EventTokenBase* At(int idx) = 0;
405  virtual const EventTokenBase* At(int idx) const = 0;
406 
407  private:
408  int m_BufferSize;
409  int m_HeadIdx;
410  int m_Num;
411 
412  Index m_EraseIndex;
413  };
414 
415 protected:
416  explicit EventCloneElementBase(EventTokenBufferBase* pEventTokenBuffer);
417 
418 protected:
419  nn::Result SetValueCore(EventTokenBase** ppTokenBase, bool isEnableSendDelay);
420  void HandleNextCore();
421  const EventTokenBase* GetHandlingEventToken() const
422  {
423  return m_pHandlingEventToken;
424  }
425 
426 
427 private:
428  enum IndexState
429  {
430  EVENT_INDEX_STATE_INVALID,
431  EVENT_INDEX_STATE_INIT,
432  EVENT_INDEX_STATE_ADJUST,
433  EVENT_INDEX_STATE_VALID
434  };
435 
436  IndexState m_IndexState;
437 
438  Index m_HandledIndex;
439  EventTokenBase* m_pHandlingEventToken;
440  Index m_PreIndex;
441 
442  EventInitialToken m_InitialToken;
443  EventTokenBufferBase* m_pEventTokenBuffer;
444 
445  bool m_IsDropEvent;
446 
447  static Definition<EventCloneElementBase> s_Definition;
448 
449 public:
450  template <int TEST_ID, typename Arg>
451  static void Test(const EventCloneElementBase& obj, Arg* pArg = NULL);
452 
453  //! @endcond
454 };
455 }
456 }
457 } // end of namespace nn::pia::clone
This is the base class for managing data that is sent and received. .
Definition: clone_CloneElementBase.h:40
This is the base class for managing the sending and receiving of events.
Definition: clone_EventCloneElementBase.h:37
u32 ClockValue
Defines a type that holds a clock value.
Definition: clone_definitions.h:44
StationIndex
Enumerates StationIndex values.
Definition: platformCtr.h:44
Definition: assert.h:115
void Trace(u64 flag) const
Prints information that is useful for debugging.
virtual ~EventCloneElementBase()
Destroys the object.
size_t GetUsingBufferNum() const
Gets the current number of event buffers in use.
bool IsDropEvent() const
Gets whether a drop event error occurred.
Definition: clone_EventCloneElementBase.h:63
u16 Id
Specifies the type of the ID for identifying clone elements.
Definition: clone_CloneElementBase.h:59
Id GetId() const
Gets the ID.
Definition: clone_CloneElementBase.h:67