CTR-Pia  5.4.3
Game Communication Engine
 全て クラス ネームスペース 関数 変数 型定義 列挙型 列挙型の値 ページ
transport_ThreadStreamManager.h
1 /*--------------------------------------------------------------------------------*
2  Copyright (C)Nintendo All rights reserved.
3 
4  These coded instructions, statements, and computer programs contain proprietary
5  information of Nintendo and/or its licensed developers and are protected by
6  national and international copyright laws. They may not be disclosed to third
7  parties or copied or duplicated in any form, in whole or in part, without the
8  prior written consent of Nintendo.
9 
10  The content herein is highly confidential and should be handled accordingly.
11  *--------------------------------------------------------------------------------*/
12 
13 
14 #pragma once
15 
16 #include <nn/pia/transport/transport_Definitions.h>
17 
18 // 先行宣言(common)
19 namespace nn
20 {
21 namespace pia
22 {
23 namespace common
24 {
25 class IPacketInput;
26 class IPacketOutput;
27 }
28 }
29 }
30 
31 
32 namespace nn
33 {
34 namespace pia
35 {
36 namespace transport
37 {
38 
39 // 先行宣言。
40 class TransportThreadStreamOld;
41 class NetworkFactory;
42 class SendThreadStream;
43 class ReceiveThreadStream;
44 
45 /*!
46  @brief 送受信スレッドを統括するクラスです。
47 
48  @details このクラスは送受信スレッドの生成/破棄などを行います。
49  また、送受信スレッドの優先度やスリープ間隔を設定する API や、
50  レイテンシエミュレーション機能のための API を用意しています。
51  このクラスのインスタンス自体は Transport クラスの初期化時に作成されます。
52 
53  */
55 {
56 public:
57 #if NN_PIA_CTR
58  static const int32_t SendThreadDefaultPriority = 10; //!< 送信スレッドのデフォルトの優先度です。
59  static const int32_t ReceiveThreadDefaultPriority = 10; //!< 受信スレッドのデフォルトの優先度です。
60 #elif NN_PIA_WIN
61  static const int32_t SendThreadDefaultPriority = THREAD_PRIORITY_ABOVE_NORMAL; //!< 送信スレッドのデフォルトの優先度です。
62  static const int32_t ReceiveThreadDefaultPriority = THREAD_PRIORITY_ABOVE_NORMAL; //!< 受信スレッドのデフォルトの優先度です。
63 #elif NN_PIA_NINTENDOSDK
64  static const int32_t SendThreadDefaultPriority = 10; //!< 送信スレッドのデフォルトの優先度です。
65  static const int32_t ReceiveThreadDefaultPriority = 10; //!< 受信スレッドのデフォルトの優先度です。
66 #elif NN_PIA_CAFE
67  static const int32_t SendThreadDefaultPriority = 10; //!< 送信スレッドのデフォルトの優先度です。
68  static const int32_t ReceiveThreadDefaultPriority = 10; //!< 受信スレッドのデフォルトの優先度です。
69 #elif NN_PIA_A
70  //n1849
71  //UIスレッド優先度を超えてはいけない
72  //0 THREAD_PRIORITY_DEFAULT アプリのスレッドとして標準的な優先度です
73  //-1 THREAD_PRIORITY_MORE_FAVORABLE 標準的な優先度より、ほんの少し優先を上げた設定値です
74  //-2 THREAD_PRIORITY_FOREGROUND UIスレッドの設定値です。システムがUIスレッドを作る際に利用します。通常、アプリ開発者は利用しません
75  static const int32_t SendThreadDefaultPriority = -1; //!< 送信スレッドのデフォルトの優先度です。
76  static const int32_t ReceiveThreadDefaultPriority = -1; //!< 受信スレッドのデフォルトの優先度です。
77 #elif NN_PIA_B
78  //todo:n3389:とりあえずな値
79  static const int32_t SendThreadDefaultPriority = -1; //!< 送信スレッドのデフォルトの優先度です。
80  static const int32_t ReceiveThreadDefaultPriority = -1; //!< 受信スレッドのデフォルトの優先度です。
81 #else
82 #error "invalid platform"
83 #endif
84 
85  static const int32_t SendThreadDefaultSleepSpan = 5; //!< 送信スレッドのデフォルトのスリープ間隔です。単位はミリ秒です。
86  static const int32_t ReceiveThreadDefaultSleepSpan = 5; //!< 受信スレッドのデフォルトのスリープ間隔です。単位はミリ秒です。
87 
88  /*!
89  @cond PRIVATE
90  @brief ThreadStreamManager クラスのインスタンスを作成します(シングルトンパターン)。
91 
92  @details この関数は Pia ライブラリ内部から呼び出されますので、アプリケーションプログラムが
93  この関数を直接呼び出す必要はありません。
94 
95  @param[in] pFactory NetworkFactory から派生した具象クラスを指すポインタ。
96  @param[in] sendThreadMaxPacketNum 送信スレッドの内部バッファ数
97  @param[in] receiveThreadMaxPacketNum 受信スレッドの内部バッファ数
98  @param[in] sendThreadLatencyEmulationPacketNum 送信レイテンシエミュレーション用バッファ数(ゼロだとエミュレーション機能は無効になります)。
99  @param[in] receiveThreadLatencyEmulationPacketNum 受信レイテンシエミュレーション用バッファ数(ゼロだとエミュレーション機能は無効になります)。
100  @param[in] bPacketLossEmulation パケロスエミュレーションを有効にするか否か
101 
102  @return インスタンスの作成に成功すれば、成功の Result が返されます。
103  @retval ResultInvalidArgument 引数が誤っています( NULL ポインタであるなど)。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
104  @retval ResultNotInitialized transport モジュールが未初期化です。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
105  @retval ResultInvalidState インスタンスを作成するタイミングが誤っています。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
106  @retval ResultAlreadyExists 既にインスタンスは作成されています。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
107  */
108  static Result CreateInstance(NetworkFactory* pFactory,
109  uint32_t sendThreadMaxPacketNum,
110  uint32_t receiveThreadMaxPacketNum,
111  uint32_t sendThreadLatencyEmulationPacketNum,
112  uint32_t receiveThreadLatencyEmulationPacketNum,
113  bool bPacketLossEmulation);
114  //! @endcond
115 
116 
117  /*!
118  @cond PRIVATE
119  @brief ThreadStreamManager クラスのインスタンスを破棄します(シングルトンパターン)。
120 
121  @details この関数は Pia ライブラリ内部から呼び出されますので、アプリケーションプログラムが
122  この関数を直接呼び出す必要はありません。
123  */
124  static void DestroyInstance(void);
125  //! @endcond
126 
127 
128  /*!
129  @brief ThreadStreamManager クラスのインスタンスを得ます(シングルトンパターン)。
130 
131  @details 事前にインスタンスが作成されていなかった場合には、
132  NULL ポインタが返されます。
133  @return ThreadStreamManager インスタンスへのポインタ。
134  */
136  {
137  return s_pInstance;
138  }
139 
140 
141  /*!
142  @cond PRIVATE
143  @brief 送受信スレッドのスタートアップ処理を実行します。
144 
145  @details この関数は Pia ライブラリ内部から呼び出されますので、アプリケーションプログラムが
146  この関数を直接呼び出す必要はありません。
147  @return 成功すれば、 IsSuccess() が true を返す Result が返されます。
148  @see Cleanup
149  */
150  Result Startup(void);
151  //! @endcond
152 
153 
154  /*!
155  @cond PRIVATE
156  @brief 送受信スレッドのクリーンアップ処理を実行します。
157 
158  @details この関数は Pia ライブラリ内部から呼び出されますので、アプリケーションプログラムが
159  この関数を直接呼び出す必要はありません。
160  @see Startup
161  */
162  void Cleanup(void);
163  //! @endcond
164 
165 
166  /*!
167  @cond PRIVATE
168  @brief デストラクタです。
169  */
170  virtual ~ThreadStreamManager(void);
171  //! @endcond
172 
173 
174  /*!
175  @brief 送信スレッドの優先度を設定します。
176 
177  @details 通常、送信スレッドの優先度は、アプリケーションが common::Scheduler::Dispatch()
178  を呼び出すスレッドの優先度よりも高くする必要があります。
179 
180  @param[in] prio 送信スレッドに指定する優先度。この値は、アプリケーションの仕様に応じて調整することを推奨します。
181  @see GetSendThreadPriority, common::Scheduler::Dispatch
182  */
183  void SetSendThreadPriority(int32_t prio);
184 
185 
186  /*!
187  @brief 送信スレッドの優先度を取得します。
188 
189  @details この関数はスレッドセーフです。
190  <br>
191  @return 送信スレッドの優先度。
192  @see SetSendThreadPriority
193  */
194  int32_t GetSendThreadPriority(void) const;
195 
196 
197  /*!
198  @brief 受信スレッドの優先度を設定します。
199 
200  @details 通常、受信スレッドの優先度は、アプリケーションが common::Scheduler::Dispatch()
201  を呼び出すスレッドの優先度よりも高くする必要があります。
202 
203  @param[in] prio 受信スレッドに指定する優先度。この値は、アプリケーションの仕様に応じて調整することを推奨します。
204  @see GetReceiveThreadPriority, common::Scheduler::Dispatch
205  */
206  void SetReceiveThreadPriority(int32_t prio);
207 
208 
209  /*!
210  @brief 受信スレッドの優先度を取得します。
211 
212  @details この関数はスレッドセーフです。
213  <br>
214  @return 受信スレッドの優先度。
215  @see SetReceiveThreadPriority
216  */
217  int32_t GetReceiveThreadPriority(void) const;
218 
219 
220  /*!
221  @brief 送信スレッドのスリープ期間を設定します。
222 
223  @details 送信スレッドは定期的にスリープします。このスリープ期間を設定する関数です。
224  <br>
225  @param[in] span 送信スレッドがスリープする期間。単位はミリ秒。この値は、アプリケーションの仕様に応じて調整することを推奨します。
226  @see GetSendThreadSleepTimeSpan
227  */
228  void SetSendThreadSleepTimeSpan(uint32_t span);
229 
230 
231  /*!
232  @brief 送信スレッドのスリープ期間を取得します。
233 
234  @details この関数はスレッドセーフです。
235  <br>
236  @return 送信スレッドのスリープ期間。単位はミリ秒。
237  @see SetSendThreadSleepTimeSpan
238  */
239  uint32_t GetSendThreadSleepTimeSpan(void) const;
240 
241 
242  /*!
243  @brief 受信スレッドのスリープ期間を設定します。
244 
245  @details 受信スレッドは定期的にスリープします。このスリープ期間を設定する関数です。
246  <br>
247  @param[in] span 受信スレッドがスリープする期間。単位はミリ秒。この値は、アプリケーションの仕様に応じて調整することを推奨します。
248  @see GetReceiveThreadSleepTimeSpan
249  */
250  void SetReceiveThreadSleepTimeSpan(uint32_t span);
251 
252 
253  /*!
254  @brief 受信スレッドのスリープ期間を取得します。
255 
256  @details この関数はスレッドセーフです。
257  <br>
258  @return 受信スレッドのスリープ期間。単位はミリ秒。
259  @see SetReceiveThreadSleepTimeSpan
260  */
261  uint32_t GetReceiveThreadSleepTimeSpan(void) const;
262 
263 
264  /*!
265  @brief 送信レイテンシエミュレーション時間を設定します。
266 
267  @details 送信レイテンシエミュレーション機能は、作成されたパケットを
268  すぐに送信するのではなく、一時的にバッファに保存し、規定の時間が
269  経過してから保存していたパケットを送信することで実現しています。
270  そのため、最大遅延時間を大きくする場合は、それに見合ったサイズの
271  バッファを用意しないと、バッファがあふれてしまい、あたかも
272  パケロスが頻発しているかのような症状を示すことがあります。
273  バッファのサイズ設定については、 Transport::DebugSetting 構造体を参照してください。
274 
275  @param[in] minLatency 最小遅延時間。単位はミリ秒です。
276  @param[in] maxLatency 最大遅延時間。単位はミリ秒です。
277  @return 成功すれば、 IsSuccess() が true を返す Result が返されます。
278  @retval ResultInvalidArgument 引数に誤りがあります。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
279  @retval ResultInvalidState レイテンシエミュレーション機能が無効の可能性があります。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
280  @see SetReceiveThreadLatencyEmulation, Transport::DebugSetting
281  */
282  Result SetSendThreadLatencyEmulation(int32_t minLatency, int32_t maxLatency);
283 
284 
285  /*!
286  @brief 受信レイテンシエミュレーション時間を設定します。
287 
288  @details 受信レイテンシエミュレーション機能は、受信したパケットを
289  すぐに上位層に渡すのではなく、一時的にバッファに保存し、規定の時間が
290  経過してから保存していたパケットを上位層に渡すことで実現しています。
291  そのため、最大遅延時間を大きくする場合は、それに見合ったサイズの
292  バッファを用意しないと、バッファがあふれてしまい、あたかも
293  パケロスが頻発しているかのような症状を示すことがあります。
294  バッファのサイズ設定については、 Transport::DebugSetting 構造体を参照してください。
295 
296  @param[in] minLatency 最小遅延時間。単位はミリ秒です。
297  @param[in] maxLatency 最大遅延時間。単位はミリ秒です。
298  @return 成功すれば、 IsSuccess() が true を返す Result が返されます。
299  @retval ResultInvalidArgument 引数に誤りがあります。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
300  @retval ResultInvalidState レイテンシエミュレーション機能が無効の可能性があります。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
301  @see SetSendThreadLatencyEmulation, Transport::DebugSetting
302  */
303  Result SetReceiveThreadLatencyEmulation(int32_t minLatency, int32_t maxLatency);
304 
305 
306  /*!
307  @brief 送信スレッドがパケットの送信を試みた回数を得ます。
308 
309  @details 送信スレッドは、送信を試みたパケットの数をカウントしています。
310  そのカウンタの値が返されます。
311 
312  @return これまでに送信を試みたパケットの総数。
313  @see ClearSendThreadSendPacketNum
314  */
315  uint32_t GetSendThreadSendPacketNum(void) const;
316 
317 
318  /*!
319  @brief 送信パケット数カウンタをクリアします。
320 
321  @details GetSendThreadSendPacketNum() で取得できる、
322  送信を試みたパケット数のカウンタをゼロにクリアします。
323 
324  @see GetSendThreadSendPacketNum
325  */
326  void ClearSendThreadSendPacketNum(void);
327 
328 
329  /*!
330  @brief 受信スレッドがパケットの受信に成功した回数を得ます。
331 
332  @details 受信スレッドは、受信に成功したパケットの数をカウントしています。
333  そのカウンタの値が返されます。
334 
335  @return これまでに受信に成功したパケットの総数。
336  @see ClearReceiveThreadReceivePacketNum
337  */
338  uint32_t GetReceiveThreadReceivePacketNum(void) const;
339 
340 
341  /*!
342  @brief 受信パケット数カウンタをクリアします。
343 
344  @details GetReceiveThreadReceivePacketNum() で取得できる、
345  受信に成功したパケット数のカウンタをゼロにクリアします。
346 
347  @see GetReceiveThreadReceivePacketNum
348  */
350 
351 
352  /*!
353  @brief 送信スレッドが送信を試みたデータの総量を得ます。
354 
355  @details 送信スレッドは、送信を試みたデータ量をカウントアップしています。
356  そのカウンタの値が返されます。
357 
358  @return これまでに送信を試みたデータの総量。単位はバイトです。
359  @see ClearSendThreadSendDataSize
360  */
361  uint64_t GetSendThreadSendDataSize(void) const;
362 
363 
364  /*!
365  @brief 送信データ量カウンタをクリアします。
366 
367  @details GetSendThreadSendDataSize() で取得できる、
368  送信を試みたデータ量のカウンタをゼロにクリアします。
369 
370  @see GetSendThreadSendDataSize
371  */
372  void ClearSendThreadSendDataSize(void);
373 
374 
375  /*!
376  @brief 受信スレッドが受信に成功したデータの総量を得ます。
377 
378  @details 受信スレッドは、受信に成功したデータ量をカウントアップしています。
379  そのカウンタの値が返されます。
380 
381  @return これまでに受信に成功したデータの総量。単位はバイトです。
382  @see ClearReceiveThreadReceiveDataSize
383  */
384  uint64_t GetReceiveThreadReceiveDataSize(void) const;
385 
386 
387  /*!
388  @brief 受信データ量カウンタをクリアします。
389 
390  @details GetReceiveThreadReceiveDataSize() で取得できる、
391  受信に成功したデータ量のカウンタをゼロにクリアします。
392 
393  @see GetReceiveThreadReceiveDataSize
394  */
396 
397 
398  /*!
399  @brief 送信スレッドがエミュレートするパケロスの確率を設定します。
400 
401  @details このパケロスエミュレーション機能を用いると、パケットの送出には
402  成功したものの、そのパケットが何らかの理由で消失したという状況を
403  エミュレートできます。
404  引数に 0% 以外の値をを設定すると、送信スレッドはその確率に応じて
405  送信パケットをドロップし、パケロスをエミュレートします。
406  デフォルトでは、送信スレッドのパケロス確率は 0% に設定されています。
407 
408  @param[in] lossPercentage 0 ~ 100 の値を設定します。
409  @return 成功すれば、 IsSuccess() が true を返す Result が返されます。
410  @retval ResultInvalidArgument 引数に誤りがあります。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
411  @retval ResultInvalidState パケロスエミュレーション機能が有効に設定されていません。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
412  @see GetSendThreadPacketLossRatio, Transport::SetDebugSetting
413  */
414  Result SetSendThreadPacketLossRatio(int32_t lossPercentage);
415 
416 
417  /*!
418  @brief 送信スレッドがエミュレートするパケロスの確率を取得します。
419 
420  @return 送信スレッドに設定されていたパケロス確率が返されます。値の範囲は 0 ~ 100 です。
421  @see SetSendThreadPacketLossRatio
422  */
423  int32_t GetSendThreadPacketLossRatio(void) const;
424 
425 
426  /*!
427  @brief 受信スレッドがエミュレートするパケロスの確率を設定します。
428 
429  @details このパケロスエミュレーション機能を用いると、こちらに向けて送出された
430  パケットが何らかの理由で消失したという状況をエミュレートできます。
431  引数に 0% 以外の値をを設定すると、受信スレッドはその確率に応じて
432  受信パケットをドロップし、パケロスをエミュレートします。
433  デフォルトでは、受信スレッドのパケロス確率は 0% に設定されています。
434 
435  @param[in] lossPercentage 0 ~ 100 の値を設定します。
436  @return 成功すれば、 IsSuccess() が true を返す Result が返されます。
437  @retval ResultInvalidArgument 引数に誤りがあります。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
438  @retval ResultInvalidState パケロスエミュレーション機能が有効に設定されていません。プログラミングエラーです。このエラーが返らないようにソースコードを修正してください。
439  @see GetReceiveThreadPacketLossRatio, Transport::SetDebugSetting
440  */
441  Result SetReceiveThreadPacketLossRatio(int32_t lossPercentage);
442 
443 
444  /*!
445  @brief 受信スレッドがエミュレートするパケロスの確率を取得します。
446 
447  @return 受信スレッドに設定されていたパケロス確率が返されます。値の範囲は 0 ~ 100 です。
448  @see SetReceiveThreadPacketLossRatio
449  */
450  int32_t GetReceiveThreadPacketLossRatio(void) const;
451 
452 
453  /*!
454  @cond PRIVATE
455  @brief ReceiveThreadStreamOld インスタンスへのポインタを得ます(非 const 版)。
456  */
457  ReceiveThreadStream* GetReceiveStream(void)
458  {
459  return m_pReceiveStream;
460  }
461  //! @endcond
462 
463 
464  /*!
465  @cond PRIVATE
466  @brief ReceiveThreadStreamOld インスタンスへのポインタを得ます( const 版)。
467  */
468  const ReceiveThreadStream* GetReceiveStream(void) const
469  {
470  return m_pReceiveStream;
471  }
472  //! @endcond
473 
474 
475  /*!
476  @cond PRIVATE
477  @brief SendThreadStreamOld インスタンスへのポインタを得ます(非 const 版)。
478  */
479  SendThreadStream* GetSendStream(void)
480  {
481  return m_pSendStream;
482  }
483  //! @endcond
484 
485 
486  /*!
487  @cond PRIVATE
488  @brief SendThreadStreamOld インスタンスへのポインタを得ます( const 版)。
489  */
490  const SendThreadStream* GetSendStream(void) const
491  {
492  return m_pSendStream;
493  }
494  //! @endcond
495 
496 
497  /*!
498  @cond PRIVATE
499  @brief NexFacade用に用意。
500  */
501  common::IPacketInput* GetInputStream(void)
502  {
503  return m_pInputStream;
504  }
505  //! @endcond
506 
507  /*!
508  @cond PRIVATE
509  @brief NexFacade用に用意。
510  */
511  common::IPacketOutput* GetOutputStream(void)
512  {
513  return m_pOutputStream;
514  }
515  //! @endcond
516 
517 
518  /*!
519  @cond PRIVATE
520  @brief モニタリングデータをセットします。
521  */
522  void SetMonitoringData(void);
523  //! @endcond
524 
525 
526  /*!
527  @brief デバッグに有用な情報をプリントします。
528 
529  @param[in] flag トレースフラグの論理和。詳細は@ref TraceFlag 型を参照してください。
530  */
531  virtual void Trace(uint64_t flag) const;
532 
533 
534 #if NN_PIA_ENABLE_STATISTIC_THREAD_STREAM_BLOCK_TIME
535  void ResetThreadStreamStatistic();
536  void PrintThreadStreamStatistic(uint32_t printMaxDataNum);
537 #endif
538 
539 private:
540  /*!
541  @brief ファクトリのポインタを与えてもらうことを大前提としているので、デフォルトコンストラクタは使いません。
542  */
543  ThreadStreamManager(void);
544 
545  /*!
546  @brief 引数ありコンストラクタです。
547  */
548  ThreadStreamManager(NetworkFactory* pFactory,
549  uint32_t sendThreadMaxPacketNum,
550  uint32_t receiveThreadMaxPacketNum,
551  uint32_t sendThreadLatencyEmulationPacketNum,
552  uint32_t receiveThreadLatencyEmulationPacketNum,
553  bool bPacketLossEmulation);
554 
555  /*!
556  @brief シングルトンパターンのため、コピーコンストラクタは封印します。
557  */
558  ThreadStreamManager(const ThreadStreamManager&);
559 
560  /*!
561  @brief シングルトンパターンのため、代入演算子は封印します。
562  */
563  ThreadStreamManager& operator=(const ThreadStreamManager&);
564 
565 
566  // ファクトリによって Create されるポインタを受ける変数。
567  common::IPacketInput* m_pInputStream;
568  common::IPacketOutput* m_pOutputStream;
569 
570  ReceiveThreadStream* m_pReceiveStream;
571  SendThreadStream* m_pSendStream;
572 
573  static ThreadStreamManager* s_pInstance;
574 };
575 }
576 }
577 } // end of namespace nn::pia::transport