SHARE
TWEET

Untitled

a guest Jan 24th, 2020 127 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. // Copyright 1998-2015 Epic Games, Inc. All Rights Reserved.
  2.  
  3. /*=============================================================================
  4.     DataChannel.h: Unreal datachannel class.
  5. =============================================================================*/
  6.  
  7. #pragma once
  8. #include "Engine/ChildConnection.h"
  9.  
  10. /*-----------------------------------------------------------------------------
  11.     UControlChannel base class.
  12. -----------------------------------------------------------------------------*/
  13.  
  14. /** network control channel message types
  15.  *
  16.  * to add a new message type, you need to:
  17.  * - add a DEFINE_CONTROL_CHANNEL_MESSAGE_* for the message type with the appropriate parameters to this file
  18.  * - add IMPLEMENT_CONTROL_CHANNEL_MESSAGE for the message type to DataChannel.cpp
  19.  * - implement the fallback behavior (eat an unparsed message) to UControlChannel::ReceivedBunch()
  20.  *
  21.  * @warning: modifying control channel messages breaks network compatibility (update GEngineMinNetVersion)
  22.  */
  23. template<uint8 MessageType> class FNetControlMessage
  24. {
  25. };
  26. /** contains info about a message type retrievable without static binding (e.g. whether it's a valid type, friendly name string, etc) */
  27. class ENGINE_API FNetControlMessageInfo
  28. {
  29. public:
  30.     static inline const TCHAR* GetName(uint8 MessageIndex)
  31.     {
  32.         CheckInitialized();
  33.         return Names[MessageIndex];
  34.     }
  35.     static inline bool IsRegistered(uint8 MessageIndex)
  36.     {
  37.         CheckInitialized();
  38.         return Names[MessageIndex][0] != 0;
  39.     }
  40.     template<uint8 MessageType> friend class FNetControlMessage;
  41. private:
  42.     static void CheckInitialized()
  43.     {
  44.         static bool bInitialized = false;
  45.         if (!bInitialized)
  46.         {
  47.             for (int32 i = 0; i < ARRAY_COUNT(Names); i++)
  48.             {
  49.                 Names[i] = TEXT("");
  50.             }
  51.             bInitialized = true;
  52.         }
  53.     }
  54.     static void SetName(uint8 MessageType, const TCHAR* InName)
  55.     {
  56.         CheckInitialized();
  57.         Names[MessageType] = InName;
  58.     }
  59.  
  60.     static const TCHAR* Names[256];
  61. };
  62.  
  63. #define DEFINE_CONTROL_CHANNEL_MESSAGE_ZEROPARAM(Name, Index) \
  64.     enum { NMT_##Name = Index }; \
  65.     template<> class FNetControlMessage<Index> \
  66.     { \
  67.     public: \
  68.         static uint8 Initialize() \
  69.         { \
  70.             FNetControlMessageInfo::SetName(Index, TEXT(#Name)); \
  71.             return 0; \
  72.         } \
  73.         /** sends a message of this type on the specified connection's control channel */ \
  74.         static void Send(UNetConnection* Conn) \
  75.         { \
  76.             static_assert(Index < 256, "Control channel message must be a byte."); \
  77.             checkSlow(!Conn->IsA(UChildConnection::StaticClass())); /** control channel messages can only be sent on the parent connection */ \
  78.             if (Conn->Channels[0] != NULL && !Conn->Channels[0]->Closing) \
  79.             { \
  80.                 FControlChannelOutBunch Bunch(Conn->Channels[0], false); \
  81.                 uint8 MessageType = Index; \
  82.                 Bunch << MessageType; \
  83.                 Conn->Channels[0]->SendBunch(&Bunch, true); \
  84.             } \
  85.         } \
  86.     };
  87. #define DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(Name, Index, TypeA) \
  88.     enum { NMT_##Name = Index }; \
  89.     template<> class FNetControlMessage<Index> \
  90.     { \
  91.     public: \
  92.         static uint8 Initialize() \
  93.         { \
  94.             FNetControlMessageInfo::SetName(Index, TEXT(#Name)); \
  95.             return 0; \
  96.         } \
  97.         /** sends a message of this type on the specified connection's control channel \
  98.          * @note: const not used only because of the FArchive interface; the parameters are not modified \
  99.          */ \
  100.         static void Send(UNetConnection* Conn, TypeA& ParamA) \
  101.         { \
  102.             static_assert(Index < 256, "Control channel message must be a byte."); \
  103.             checkSlow(!Conn->IsA(UChildConnection::StaticClass())); /** control channel messages can only be sent on the parent connection */ \
  104.             if (Conn->Channels[0] != NULL && !Conn->Channels[0]->Closing) \
  105.             { \
  106.                 FControlChannelOutBunch Bunch(Conn->Channels[0], false); \
  107.                 uint8 MessageType = Index; \
  108.                 Bunch << MessageType; \
  109.                 Bunch << ParamA; \
  110.                 Conn->Channels[0]->SendBunch(&Bunch, true); \
  111.             } \
  112.         } \
  113.         /** receives a message of this type from the passed in bunch */ \
  114.         static void Receive(FInBunch& Bunch, TypeA& ParamA) \
  115.         { \
  116.             Bunch << ParamA; \
  117.         } \
  118.         /** throws away a message of this type from the passed in bunch */ \
  119.         static void Discard(FInBunch& Bunch) \
  120.         { \
  121.             TypeA ParamA; \
  122.             Receive(Bunch, ParamA); \
  123.         } \
  124.     };
  125. #define DEFINE_CONTROL_CHANNEL_MESSAGE_TWOPARAM(Name, Index, TypeA, TypeB) \
  126.     enum { NMT_##Name = Index }; \
  127.     template<> class FNetControlMessage<Index> \
  128.     { \
  129.     public: \
  130.         static uint8 Initialize() \
  131.         { \
  132.             FNetControlMessageInfo::SetName(Index, TEXT(#Name)); \
  133.             return 0; \
  134.         } \
  135.         /** sends a message of this type on the specified connection's control channel \
  136.          * @note: const not used only because of the FArchive interface; the parameters are not modified \
  137.          */ \
  138.         static void Send(UNetConnection* Conn, TypeA& ParamA, TypeB& ParamB) \
  139.         { \
  140.             static_assert(Index < 256, "Control channel message must be a byte."); \
  141.             checkSlow(!Conn->IsA(UChildConnection::StaticClass())); /** control channel messages can only be sent on the parent connection */ \
  142.             if (Conn->Channels[0] != NULL && !Conn->Channels[0]->Closing) \
  143.             { \
  144.                 FControlChannelOutBunch Bunch(Conn->Channels[0], false); \
  145.                 uint8 MessageType = Index; \
  146.                 Bunch << MessageType; \
  147.                 Bunch << ParamA; \
  148.                 Bunch << ParamB; \
  149.                 Conn->Channels[0]->SendBunch(&Bunch, true); \
  150.             } \
  151.         } \
  152.         static void Receive(FInBunch& Bunch, TypeA& ParamA, TypeB& ParamB) \
  153.         { \
  154.             Bunch << ParamA; \
  155.             Bunch << ParamB; \
  156.         } \
  157.         /** throws away a message of this type from the passed in bunch */ \
  158.         static void Discard(FInBunch& Bunch) \
  159.         { \
  160.             TypeA ParamA; \
  161.             TypeB ParamB; \
  162.             Receive(Bunch, ParamA, ParamB); \
  163.         } \
  164.     };
  165. #define DEFINE_CONTROL_CHANNEL_MESSAGE_THREEPARAM(Name, Index, TypeA, TypeB, TypeC) \
  166.     enum { NMT_##Name = Index }; \
  167.     template<> class FNetControlMessage<Index> \
  168.     { \
  169.     public: \
  170.         static uint8 Initialize() \
  171.         { \
  172.             FNetControlMessageInfo::SetName(Index, TEXT(#Name)); \
  173.             return 0; \
  174.         } \
  175.         /** sends a message of this type on the specified connection's control channel \
  176.          * @note: const not used only because of the FArchive interface; the parameters are not modified \
  177.          */ \
  178.         static void Send(UNetConnection* Conn, TypeA& ParamA, TypeB& ParamB, TypeC& ParamC) \
  179.         { \
  180.             static_assert(Index < 256, "Control channel message must be a byte."); \
  181.             checkSlow(!Conn->IsA(UChildConnection::StaticClass())); /** control channel messages can only be sent on the parent connection */ \
  182.             if (Conn->Channels[0] != NULL && !Conn->Channels[0]->Closing) \
  183.             { \
  184.                 FControlChannelOutBunch Bunch(Conn->Channels[0], false); \
  185.                 uint8 MessageType = Index; \
  186.                 Bunch << MessageType; \
  187.                 Bunch << ParamA; \
  188.                 Bunch << ParamB; \
  189.                 Bunch << ParamC; \
  190.                 Conn->Channels[0]->SendBunch(&Bunch, true); \
  191.             } \
  192.         } \
  193.         static void Receive(FInBunch& Bunch, TypeA& ParamA, TypeB& ParamB, TypeC& ParamC) \
  194.         { \
  195.             Bunch << ParamA; \
  196.             Bunch << ParamB; \
  197.             Bunch << ParamC; \
  198.         } \
  199.         /** throws away a message of this type from the passed in bunch */ \
  200.         static void Discard(FInBunch& Bunch) \
  201.         { \
  202.             TypeA ParamA; \
  203.             TypeB ParamB; \
  204.             TypeC ParamC; \
  205.             Receive(Bunch, ParamA, ParamB, ParamC); \
  206.         } \
  207.     };
  208. #define DEFINE_CONTROL_CHANNEL_MESSAGE_FOURPARAM(Name, Index, TypeA, TypeB, TypeC, TypeD) \
  209.     enum { NMT_##Name = Index }; \
  210.     template<> class FNetControlMessage<Index> \
  211.     { \
  212.     public: \
  213.         static uint8 Initialize() \
  214.         { \
  215.             FNetControlMessageInfo::SetName(Index, TEXT(#Name)); \
  216.             return 0; \
  217.         } \
  218.         /** sends a message of this type on the specified connection's control channel \
  219.          * @note: const not used only because of the FArchive interface; the parameters are not modified \
  220.          */ \
  221.         static void Send(UNetConnection* Conn, TypeA& ParamA, TypeB& ParamB, TypeC& ParamC, TypeD& ParamD) \
  222.         { \
  223.             static_assert(Index < 256, "Control channel message must be a byte."); \
  224.             checkSlow(!Conn->IsA(UChildConnection::StaticClass())); /** control channel messages can only be sent on the parent connection */ \
  225.             if (Conn->Channels[0] != NULL && !Conn->Channels[0]->Closing) \
  226.             { \
  227.                 FControlChannelOutBunch Bunch(Conn->Channels[0], false); \
  228.                 uint8 MessageType = Index; \
  229.                 Bunch << MessageType; \
  230.                 Bunch << ParamA; \
  231.                 Bunch << ParamB; \
  232.                 Bunch << ParamC; \
  233.                 Bunch << ParamD; \
  234.                 Conn->Channels[0]->SendBunch(&Bunch, true); \
  235.             } \
  236.         } \
  237.         static void Receive(FInBunch& Bunch, TypeA& ParamA, TypeB& ParamB, TypeC& ParamC, TypeD& ParamD) \
  238.         { \
  239.             Bunch << ParamA; \
  240.             Bunch << ParamB; \
  241.             Bunch << ParamC; \
  242.             Bunch << ParamD; \
  243.         } \
  244.         /** throws away a message of this type from the passed in bunch */ \
  245.         static void Discard(FInBunch& Bunch) \
  246.         { \
  247.             TypeA ParamA; \
  248.             TypeB ParamB; \
  249.             TypeC ParamC; \
  250.             TypeD ParamD; \
  251.             Receive(Bunch, ParamA, ParamB, ParamC, ParamD); \
  252.         } \
  253.     };
  254.  
  255. #define DEFINE_CONTROL_CHANNEL_MESSAGE_SEVENPARAM(Name, Index, TypeA, TypeB, TypeC, TypeD, TypeE, TypeF, TypeG) \
  256.     enum { NMT_##Name = Index }; \
  257.     template<> class FNetControlMessage<Index> \
  258.     { \
  259.     public: \
  260.         static uint8 Initialize() \
  261.         { \
  262.             FNetControlMessageInfo::SetName(Index, TEXT(#Name)); \
  263.             return 0; \
  264.         } \
  265.         /** sends a message of this type on the specified connection's control channel \
  266.          * @note: const not used only because of the FArchive interface; the parameters are not modified \
  267.          */ \
  268.         static void Send(UNetConnection* Conn, TypeA& ParamA, TypeB& ParamB, TypeC& ParamC, TypeD& ParamD, TypeE& ParamE, TypeF& ParamF, TypeG& ParamG) \
  269.         { \
  270.             static_assert(Index < 256, "Control channel message must be a byte."); \
  271.             checkSlow(!Conn->IsA(UChildConnection::StaticClass())); /** control channel messages can only be sent on the parent connection */ \
  272.             if (Conn->Channels[0] != NULL && !Conn->Channels[0]->Closing) \
  273.             { \
  274.                 FControlChannelOutBunch Bunch(Conn->Channels[0], false); \
  275.                 uint8 MessageType = Index; \
  276.                 Bunch << MessageType; \
  277.                 Bunch << ParamA; \
  278.                 Bunch << ParamB; \
  279.                 Bunch << ParamC; \
  280.                 Bunch << ParamD; \
  281.                 Bunch << ParamE; \
  282.                 Bunch << ParamF; \
  283.                 Bunch << ParamG; \
  284.                 Conn->Channels[0]->SendBunch(&Bunch, true); \
  285.             } \
  286.         } \
  287.         static void Receive(FInBunch& Bunch, TypeA& ParamA, TypeB& ParamB, TypeC& ParamC, TypeD& ParamD, TypeE& ParamE, TypeF& ParamF, TypeG& ParamG) \
  288.         { \
  289.             Bunch << ParamA; \
  290.             Bunch << ParamB; \
  291.             Bunch << ParamC; \
  292.             Bunch << ParamD; \
  293.             Bunch << ParamE; \
  294.             Bunch << ParamF; \
  295.             Bunch << ParamG; \
  296.         } \
  297.         /** throws away a message of this type from the passed in bunch */ \
  298.         static void Discard(FInBunch& Bunch) \
  299.         { \
  300.             TypeA ParamA; \
  301.             TypeB ParamB; \
  302.             TypeC ParamC; \
  303.             TypeD ParamD; \
  304.             TypeE ParamE; \
  305.             TypeF ParamF; \
  306.             TypeG ParamG; \
  307.             Receive(Bunch, ParamA, ParamB, ParamC, ParamD, ParamE, ParamF, ParamG); \
  308.         } \
  309.     };
  310.  
  311. #define DEFINE_CONTROL_CHANNEL_MESSAGE_EIGHTPARAM(Name, Index, TypeA, TypeB, TypeC, TypeD, TypeE, TypeF, TypeG, TypeH) \
  312.     enum { NMT_##Name = Index }; \
  313.     template<> class FNetControlMessage<Index> \
  314.     { \
  315.     public: \
  316.         static uint8 Initialize() \
  317.         { \
  318.             FNetControlMessageInfo::SetName(Index, TEXT(#Name)); \
  319.             return 0; \
  320.         } \
  321.         /** sends a message of this type on the specified connection's control channel \
  322.          * @note: const not used only because of the FArchive interface; the parameters are not modified \
  323.          */ \
  324.         static void Send(UNetConnection* Conn, TypeA& ParamA, TypeB& ParamB, TypeC& ParamC, TypeD& ParamD, TypeE& ParamE, TypeF& ParamF, TypeG& ParamG, TypeH& ParamH) \
  325.         { \
  326.             static_assert(Index < 256, "Control channel message must be a byte."); \
  327.             checkSlow(!Conn->IsA(UChildConnection::StaticClass())); /** control channel messages can only be sent on the parent connection */ \
  328.             if (Conn->Channels[0] != NULL && !Conn->Channels[0]->Closing) \
  329.             { \
  330.                 FControlChannelOutBunch Bunch(Conn->Channels[0], false); \
  331.                 uint8 MessageType = Index; \
  332.                 Bunch << MessageType; \
  333.                 Bunch << ParamA; \
  334.                 Bunch << ParamB; \
  335.                 Bunch << ParamC; \
  336.                 Bunch << ParamD; \
  337.                 Bunch << ParamE; \
  338.                 Bunch << ParamF; \
  339.                 Bunch << ParamG; \
  340.                 Bunch << ParamH; \
  341.                 Conn->Channels[0]->SendBunch(&Bunch, true); \
  342.             } \
  343.         } \
  344.         static void Receive(FInBunch& Bunch, TypeA& ParamA, TypeB& ParamB, TypeC& ParamC, TypeD& ParamD, TypeE& ParamE, TypeF& ParamF, TypeG& ParamG, TypeH& ParamH) \
  345.         { \
  346.             Bunch << ParamA; \
  347.             Bunch << ParamB; \
  348.             Bunch << ParamC; \
  349.             Bunch << ParamD; \
  350.             Bunch << ParamE; \
  351.             Bunch << ParamF; \
  352.             Bunch << ParamG; \
  353.             Bunch << ParamH; \
  354.         } \
  355.         /** throws away a message of this type from the passed in bunch */ \
  356.         static void Discard(FInBunch& Bunch) \
  357.         { \
  358.             TypeA ParamA; \
  359.             TypeB ParamB; \
  360.             TypeC ParamC; \
  361.             TypeD ParamD; \
  362.             TypeE ParamE; \
  363.             TypeF ParamF; \
  364.             TypeG ParamG; \
  365.             TypeH ParamH; \
  366.             Receive(Bunch, ParamA, ParamB, ParamC, ParamD, ParamE, ParamF, ParamG, ParamH); \
  367.         } \
  368.     };
  369.  
  370. #define IMPLEMENT_CONTROL_CHANNEL_MESSAGE(Name) static uint8 Dummy##_FNetControlMessage_##Name = FNetControlMessage<NMT_##Name>::Initialize();
  371.  
  372. // message type definitions
  373. DEFINE_CONTROL_CHANNEL_MESSAGE_TWOPARAM(Hello, 0, uint8, uint32); // initial client connection message
  374. DEFINE_CONTROL_CHANNEL_MESSAGE_THREEPARAM(Welcome, 1, FString, FString, FString); // server tells client they're ok'ed to load the server's level
  375. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(Upgrade, 2, uint32); // server tells client their version is incompatible
  376. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(Challenge, 3, FString); // server sends client challenge string to verify integrity
  377. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(Netspeed, 4, int32); // client sends requested transfer rate
  378. DEFINE_CONTROL_CHANNEL_MESSAGE_THREEPARAM(Login, 5, FString, FString, FUniqueNetIdRepl); // client requests to be admitted to the game
  379. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(Failure, 6, FString); // indicates connection failure
  380. DEFINE_CONTROL_CHANNEL_MESSAGE_ZEROPARAM(Join, 9); // final join request (spawns PlayerController)
  381. DEFINE_CONTROL_CHANNEL_MESSAGE_TWOPARAM(JoinSplit, 10, FString, FUniqueNetIdRepl); // child player (splitscreen) join request
  382. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(Skip, 12, FGuid); // client request to skip an optional package
  383. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(Abort, 13, FGuid); // client informs server that it aborted a not-yet-verified package due to an UNLOAD request
  384. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(PCSwap, 15, int32); // client tells server it has completed a swap of its Connection->Actor
  385. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(ActorChannelFailure, 16, int32); // client tells server that it failed to open an Actor channel sent by the server (e.g. couldn't serialize Actor archetype)
  386. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(DebugText, 17, FString); // debug text sent to all clients or to server
  387. DEFINE_CONTROL_CHANNEL_MESSAGE_TWOPARAM(NetGUIDAssign, 18, FNetworkGUID, FString); // Explicit NetworkGUID assignment. This is rare and only happens if a netguid is only serialized client->server (this msg goes server->client to tell client what ID to use in that case)
  388.  
  389. //          Beacon control channel flow
  390. // Client                                               Server
  391. //  Send<Hello>
  392. //                                                      Receive<Hello> - compare version / game id
  393. //                                                          Send<Upgrade> if incompatible
  394. //                                                          Send<Failure> if wrong game
  395. //                                                          Send<BeaconWelcome> if good so far
  396. //  Receive<BeaconWelcome>
  397. //      Send<NetSpeed>
  398. //      Send<BeaconJoin> with beacon type
  399. //                                                      Receive<Netspeed>
  400. //                                                      Receive<BeaconJoin> - create requested beacon type and create NetGUID
  401. //                                                          Send<Failure> if unable to create or bad type
  402. //                                                          Send<BeaconAssignGUID> with NetGUID for new beacon actor
  403. //  Receive<BeaconAssignGUID> - assign NetGUID to client actor
  404. //      Send<BeaconNetGUIDAck> acknowledging receipt of NetGUID
  405. //                                                      Receive<BeaconNetGUIDAck> - connection complete
  406.  
  407. DEFINE_CONTROL_CHANNEL_MESSAGE_ZEROPARAM(BeaconWelcome, 25); // server tells client they're ok to attempt to join (client sends netspeed/beacontype)
  408. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(BeaconJoin, 26, FString);  // server tries to create beacon type requested by client, sends NetGUID for actor sync
  409. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(BeaconAssignGUID, 27, FNetworkGUID); // client assigns NetGUID from server to beacon actor, sends NetGUIDAck
  410. DEFINE_CONTROL_CHANNEL_MESSAGE_ONEPARAM(BeaconNetGUIDAck, 28, FString); // server received NetGUIDAck from client, connection established successfully
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
Top