DataStreamDefinitions

DataStreamDefinitions

#Overview

name: DataStreamDefinitions

The value of this variable can be defined or overridden in .ini config files. 2 .ini config files referencing this setting variable.

It is referenced in 11 C++ source files.

#Summary

#Usage in the C++ source code

The purpose of DataStreamDefinitions is to manage and define data streams used in the Unreal Engine’s replication system, specifically within the Iris networking framework. It serves as a configuration and management tool for data streams, which are likely used for efficient network communication in multiplayer games or networked applications.

DataStreamDefinitions is primarily used in the Iris Core module, which is part of the experimental Iris networking system in Unreal Engine. It’s also referenced in the ReplicationSystemTestPlugin, indicating its importance in the replication and networking subsystems.

The value of this variable is set through configuration (UPROPERTY(Config)) and can be modified programmatically. It’s stored as an array of FDataStreamDefinition structures within the UDataStreamDefinitions class.

Several other variables interact with DataStreamDefinitions:

  1. bFixupComplete: A boolean flag indicating whether the definitions have been properly set up.
  2. DataStreamName: Used to identify individual data streams.
  3. ClassName: Specifies the class for each data stream.
  4. DefaultSendStatus: Defines the default sending behavior for the data stream.

Developers must be aware of the following when using this variable:

  1. Ensure unique names for each data stream to avoid conflicts.
  2. Properly load and set up the classes specified for each data stream.
  3. Use valid EDataStreamSendStatus values for the DefaultSendStatus.
  4. Call FixupDefinitions() after modifying the definitions to ensure proper setup.

Best practices when using this variable include:

  1. Use the provided methods (FindDefinition, GetAutoCreateStreamNames) to interact with the definitions rather than accessing the array directly.
  2. Avoid duplicate stream names to prevent errors and unexpected behavior.
  3. Ensure that specified classes inherit from UDataStream and can be loaded.
  4. Use the WITH_AUTOMATION_WORKER preprocessor directive for testing purposes only, not in production code.
  5. Always verify that FixupDefinitions() has been called before using the data streams in the actual networking code.

#Setting Variables

#References In INI files

Location: <Workspace>/Engine/Config/BaseEngine.ini:1303, section: [/Script/IrisCore.DataStreamDefinitions]

Location: <Workspace>/Engine/Config/BaseEngine.ini:1304, section: [/Script/IrisCore.DataStreamDefinitions]

#References in C++ code

#Callsites

This variable is referenced in the following C++ source code:

#Loc: <Workspace>/Engine/Plugins/Runtime/ReplicationSystemTestPlugin/Source/Private/Tests/DataStream/TestDataStream.cpp:16

Scope (from outer to inner):

file
namespace    UE::Net::Private

Source code excerpt:

{

// These test cannot run in parallel with other code accessing data streams, like DataStreamManager and DataStreamDefinitions.
class FTestDataStream : public FNetworkAutomationTestSuiteFixture
{
public:
	FTestDataStream();

	virtual void SetUp() override;

#Loc: <Workspace>/Engine/Plugins/Runtime/ReplicationSystemTestPlugin/Source/Private/Tests/DataStream/TestDataStream.cpp:43

Scope (from outer to inner):

file
namespace    UE::Net::Private
class        class FTestDataStream : public FNetworkAutomationTestSuiteFixture

Source code excerpt:


	UDataStreamManager* DataStreamManager;
	UMyDataStreamDefinitions* DataStreamDefinitions;
	TArray<FDataStreamDefinition>* CurrentDataStreamDefinitions;
	TArray<FDataStreamDefinition> PreviousDataStreamDefinitions;
	bool* PointerToFixupComplete;

	//
	FNetSerializationContext DataStreamContext;

#Loc: <Workspace>/Engine/Plugins/Runtime/ReplicationSystemTestPlugin/Source/Private/Tests/DataStream/TestDataStream.cpp:196

Scope (from outer to inner):

file
namespace    UE::Net::Private
function     FTestDataStream::FTestDataStream

Source code excerpt:

: FNetworkAutomationTestSuiteFixture()
, DataStreamManager(nullptr)
, DataStreamDefinitions(nullptr)
, CurrentDataStreamDefinitions(nullptr)
, DataStreamContext(&BitStreamReader, &BitStreamWriter)
{
}

void FTestDataStream::SetUp()

#Loc: <Workspace>/Engine/Plugins/Runtime/ReplicationSystemTestPlugin/Source/Private/Tests/DataStream/TestDataStream.cpp:220

Scope (from outer to inner):

file
namespace    UE::Net::Private
function     void FTestDataStream::StoreDataStreamDefinitions

Source code excerpt:

void FTestDataStream::StoreDataStreamDefinitions()
{
	DataStreamDefinitions = static_cast<UMyDataStreamDefinitions*>(GetMutableDefault<UDataStreamDefinitions>());
	check(DataStreamDefinitions != nullptr);
	CurrentDataStreamDefinitions = &DataStreamDefinitions->ReadWriteDataStreamDefinitions();
	PointerToFixupComplete = &DataStreamDefinitions->ReadWriteFixupComplete();

	PreviousDataStreamDefinitions.Empty();
	Swap(*CurrentDataStreamDefinitions, PreviousDataStreamDefinitions);
	*PointerToFixupComplete = false;
}

#Loc: <Workspace>/Engine/Plugins/Runtime/ReplicationSystemTestPlugin/Source/Private/Tests/DataStream/TestDataStream.cpp:250

Scope (from outer to inner):

file
namespace    UE::Net::Private
function     void FTestDataStream::AddMockDataStreamDefinition

Source code excerpt:

	CreateMockDataStreamDefinition(Definition, bValid);
	CurrentDataStreamDefinitions->Add(Definition);
	DataStreamDefinitions->FixupDefinitions();
}

UMockDataStream* FTestDataStream::CreateMockStream(const UMockDataStream::FFunctionCallSetup* Setup)
{
	AddMockDataStreamDefinition(true);
	DataStreamManager->CreateStream("Mock");

#Loc: <Workspace>/Engine/Plugins/Runtime/ReplicationSystemTestPlugin/Source/Private/Tests/ReplicationSystem/ReplicationSystemServerClientTestFixture.cpp:15

Scope (from outer to inner):

file
namespace    UE::Net
function     FDataStreamTestUtil::FDataStreamTestUtil

Source code excerpt:

// FDataStreamTestUtil implementation
FDataStreamTestUtil::FDataStreamTestUtil()
: DataStreamDefinitions(nullptr)
, CurrentDataStreamDefinitions(nullptr)
{
}

void FDataStreamTestUtil::SetUp()
{

#Loc: <Workspace>/Engine/Plugins/Runtime/ReplicationSystemTestPlugin/Source/Private/Tests/ReplicationSystem/ReplicationSystemServerClientTestFixture.cpp:32

Scope (from outer to inner):

file
namespace    UE::Net
function     void FDataStreamTestUtil::StoreDataStreamDefinitions

Source code excerpt:

void FDataStreamTestUtil::StoreDataStreamDefinitions()
{
	DataStreamDefinitions = static_cast<UMyDataStreamDefinitions*>(GetMutableDefault<UDataStreamDefinitions>());
	check(DataStreamDefinitions != nullptr);
	CurrentDataStreamDefinitions = &DataStreamDefinitions->ReadWriteDataStreamDefinitions();
	PointerToFixupComplete = &DataStreamDefinitions->ReadWriteFixupComplete();

	PreviousDataStreamDefinitions.Empty();
	Swap(*CurrentDataStreamDefinitions, PreviousDataStreamDefinitions);
	*PointerToFixupComplete = false;
}

#Loc: <Workspace>/Engine/Plugins/Runtime/ReplicationSystemTestPlugin/Source/Private/Tests/ReplicationSystem/ReplicationSystemServerClientTestFixture.h:38

Scope (from outer to inner):

file
namespace    UE::Net
class        class FDataStreamTestUtil
function     void FixupDefinitions

Source code excerpt:

	void RestoreDataStreamDefinitions();
	void AddDataStreamDefinition(const TCHAR* StreamName, const TCHAR* ClassPath, bool bValid = true);
	void FixupDefinitions() { DataStreamDefinitions->FixupDefinitions(); }

protected:
	UMyDataStreamDefinitions* DataStreamDefinitions;
	TArray<FDataStreamDefinition>* CurrentDataStreamDefinitions;
	TArray<FDataStreamDefinition> PreviousDataStreamDefinitions;
	bool* PointerToFixupComplete;
};

// Implements everything we need to drive the replication system to test the system

#Loc: <Workspace>/Engine/Source/Runtime/Experimental/Iris/Core/Private/Iris/DataStream/DataStreamDefinitions.cpp:17

Scope (from outer to inner):

file
function     void UDataStreamDefinitions::FixupDefinitions

Source code excerpt:

	}

	for (FDataStreamDefinition& Definition : DataStreamDefinitions)
	{
		UE_CLOG(DataStreamDefinitions.ContainsByPredicate([Name = Definition.DataStreamName, &Definition](const FDataStreamDefinition& ExistingDefinition) { return Name == ExistingDefinition.DataStreamName && &Definition != &ExistingDefinition; }), LogIris, Error, TEXT("DataStream name is defined multiple times: %s."), *Definition.DataStreamName.GetPlainNameString());
		UE_CLOG(!StaticEnum<EDataStreamSendStatus>()->IsValidEnumValue(int8(Definition.DefaultSendStatus)), LogIris, Error, TEXT("Invalid DataStreamSendStatus %u for DataStream %s."), unsigned(Definition.DefaultSendStatus), *Definition.DataStreamName.GetPlainNameString());

		Definition.Class = StaticLoadClass(UDataStream::StaticClass(), nullptr, *Definition.ClassName.ToString(), nullptr, LOAD_Quiet);

		UE_CLOG(Definition.Class == nullptr, LogIris, Error, TEXT("DataStream class could not be loaded: %s"), *Definition.ClassName.GetPlainNameString());
	}

#Loc: <Workspace>/Engine/Source/Runtime/Experimental/Iris/Core/Private/Iris/DataStream/DataStreamDefinitions.cpp:32

Scope (from outer to inner):

file
function     const FDataStreamDefinition* UDataStreamDefinitions::FindDefinition

Source code excerpt:

const FDataStreamDefinition* UDataStreamDefinitions::FindDefinition(const FName Name) const
{
	return DataStreamDefinitions.FindByPredicate([Name](const FDataStreamDefinition& Definition) { return Name == Definition.DataStreamName; });
}

void UDataStreamDefinitions::GetAutoCreateStreamNames(TArray<FName>& OutStreamNames) const
{
	for (const FDataStreamDefinition& Definition : DataStreamDefinitions)
	{
		if (Definition.bAutoCreate)
		{
			OutStreamNames.Add(Definition.DataStreamName);
		}
	}

#Loc: <Workspace>/Engine/Source/Runtime/Experimental/Iris/Core/Private/Iris/DataStream/DataStreamDefinitions.h:50

Scope (from outer to inner):

file
class        class UDataStreamDefinitions : public UObject

Source code excerpt:

private:
	UPROPERTY(Config)
	TArray<FDataStreamDefinition> DataStreamDefinitions;

	bool bFixupComplete;

// For testing purposes only
#if WITH_AUTOMATION_WORKER
public:
	inline TArray<FDataStreamDefinition>& ReadWriteDataStreamDefinitions() { return DataStreamDefinitions; }
	inline bool& ReadWriteFixupComplete() { return bFixupComplete; }
#endif
};