Struct MultiNetworkDriver
The MultiNetworkDriver
structure is a way to manipulate multiple instances of
NetworkDriver at the same time. This abstraction is meant to make it easy to
work with servers that must accept different connection types (e.g. both UDP and WebSocket
connections). This is useful for cross-play support across different platforms.
Inherited Members
Namespace: Unity.Networking.Transport
Syntax
public struct MultiNetworkDriver : IDisposable
Examples
This code below shows how to create a MultiNetworkDriver
that accepts both UDP and
WebSocket connections.
var udpDriver = NetworkDriver.Create(new UDPNetworkInterface());
udpDriver.Bind(NetworkEndpoint.AnyIpv4.WithPort(7777)); // UDP port
udpDriver.Listen();
var wsDriver = NetworkDriver.Create(new WebSocketNetworkInterface());
wsDriver.Bind(NetworkEndpoint.AnyIpv4.WithPort(7777)); // TCP port
wsDriver.Listen();
var multiDriver = MultiNetworkDriver.Create();
multiDriver.AddDriver(udpDriver);
multiDriver.AddDriver(wsDriver);
The created MultiNetworkDriver
can then be used as one would use a
NetworkDriver since they share most of the same APIs.
Fields
MaxDriverCount
The maximum number of drivers that can be added to a MultiNetworkDriver
.
Declaration
public const int MaxDriverCount = 4
Field Value
Type | Description |
---|---|
Int32 | Number of drivers. |
Properties
DriverCount
Number of drivers that have been added.
Declaration
public int DriverCount { readonly get; }
Property Value
Type | Description |
---|---|
Int32 | Number of drivers. |
IsCreated
Whether the MultiNetworkDriver
has been created.
Declaration
public readonly bool IsCreated { get; }
Property Value
Type | Description |
---|---|
Boolean | True if created, false otherwise. |
Methods
AbortSend(DataStreamWriter)
Aborts a send started with BeginSend(NetworkPipeline, NetworkConnection, out DataStreamWriter, Int32).
Declaration
public void AbortSend(DataStreamWriter writer)
Parameters
Type | Name | Description |
---|---|---|
DataStreamWriter | writer | DataStreamWriter to cancel. |
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
Accept()
Accept any new incoming connections. Connections must be accepted before data can be sent on them. It's also the only way to obtain the NetworkConnection value for new connections on servers.
Declaration
public NetworkConnection Accept()
Returns
Type | Description |
---|---|
NetworkConnection | New connection if any, otherwise a default-value object. |
AddDriver(NetworkDriver)
Add a NetworkDriver instance to the MultiNetworkDriver
. This driver
instance must not already have any active connections, and must have the same number of
pipelines as previously added instances. Drivers that are intended to take on a server
role must also already be in the listening state.
Declaration
public int AddDriver(NetworkDriver driver)
Parameters
Type | Name | Description |
---|---|---|
NetworkDriver | driver | NetworkDriver instance to add. |
Returns
Type | Description |
---|---|
Int32 | An ID identifying the NetworkDriver inside the |
Remarks
The MultiNetworkDriver
takes ownership of the NetworkDriver. While
it is possible to keep operating on the NetworkDriver once it's been
added, this is not recommended (at least for the operations that are already covered by
the MultiNetworkDriver
API).
Exceptions
Type | Condition |
---|---|
InvalidOperationException | If the |
ArgumentException | If the driver already has active connections, or if it doesn't have as many pipelines as previously added drivers. Note that this exception is only thrown when safety checks are enabled (i.e. in the editor), otherwise the driver will be added anyway. |
BeginSend(NetworkConnection, out DataStreamWriter, Int32)
Begin sending data on the given connection (default pipeline).
Declaration
public int BeginSend(NetworkConnection connection, out DataStreamWriter writer, int requiredPayloadSize = 0)
Parameters
Type | Name | Description |
---|---|---|
NetworkConnection | connection | Connection to send the data to. |
DataStreamWriter | writer | DataStreamWriter the data can be written to. |
Int32 | requiredPayloadSize | Size that the returned DataStreamWriter must support. The method will return an error if that payload size is not supported by the pipeline. Defaults to 0, which means the DataStreamWriter will be as large as it can be. |
Returns
Type | Description |
---|---|
Int32 | 0 on success, a negative value on error. |
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
BeginSend(NetworkPipeline, NetworkConnection, out DataStreamWriter, Int32)
Begin sending data on the given connection and pipeline.
Declaration
public int BeginSend(NetworkPipeline pipe, NetworkConnection connection, out DataStreamWriter writer, int requiredPayloadSize = 0)
Parameters
Type | Name | Description |
---|---|---|
NetworkPipeline | pipe | Pipeline to send the data on. |
NetworkConnection | connection | Connection to send the data to. |
DataStreamWriter | writer | DataStreamWriter the data can be written to. |
Int32 | requiredPayloadSize | Size that the returned DataStreamWriter must support. The method will return an error if that payload size is not supported by the pipeline. Defaults to 0, which means the DataStreamWriter will be as large as it can be. |
Returns
Type | Description |
---|---|
Int32 | 0 on success, a negative error code on error. |
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
Connect(Int32, NetworkEndpoint)
Establish a new connection to the given endpoint. Note that this only starts establishing the new connection. From there it will either succeeds (a Connect event will pop on the connection) or fail (a Disconnect event will pop on the connection) at a later time.
Declaration
public NetworkConnection Connect(int driverId, NetworkEndpoint endpoint)
Parameters
Type | Name | Description |
---|---|---|
Int32 | driverId | ID of the driver to connect, as obtained with AddDriver(NetworkDriver). |
NetworkEndpoint | endpoint |
Returns
Type | Description |
---|---|
NetworkConnection | New connection object, or a default-valued object on failure. |
Remarks
Establishing a new connection normally requires the driver to be bound (e.g. with the
Bind(NetworkEndpoint) method), but if that's not the case when calling this method, the
driver will be implicitly bound to the appropriate wildcard address. This is a behavior
similar to BSD sockets, where calling connect
automatically binds the socket to
an ephemeral port.
Create()
Create a new MultiNetworkDriver
instance.
Declaration
public static MultiNetworkDriver Create()
Returns
Type | Description |
---|---|
MultiNetworkDriver | The new |
CreatePipeline(Type[])
Create a new pipeline from stage types.
Declaration
public NetworkPipeline CreatePipeline(params Type[] stages)
Parameters
Type | Name | Description |
---|---|---|
Type[] | stages | Array of stages the pipeline should contain. |
Returns
Type | Description |
---|---|
NetworkPipeline |
Remarks
The order of the different stages is important, as that is the order in which the stages will process a packet when sending messages (the reverse order is used when processing received packets).
Exceptions
Type | Condition |
---|---|
InvalidOperationException | If called after the driver has established connections or before it is created. Note this is only thrown if safety checks are enabled (i.e. in the editor). |
CreatePipeline(NativeArray<NetworkPipelineStageId>)
Create a new pipeline from stage types.
Declaration
public NetworkPipeline CreatePipeline(NativeArray<NetworkPipelineStageId> stages)
Parameters
Type | Name | Description |
---|---|---|
NativeArray<NetworkPipelineStageId> | stages |
Returns
Type | Description |
---|---|
NetworkPipeline |
Remarks
The order of the different stages is important, as that is the order in which the stages will process a packet when sending messages (the reverse order is used when processing received packets).
Exceptions
Type | Condition |
---|---|
InvalidOperationException | If called after the driver has established connections or before it is created. Note this is only thrown if safety checks are enabled (i.e. in the editor). |
Disconnect(NetworkConnection)
Close a connection. Note that to properly notify a peer of this disconnection, it is required to schedule at least one update with ScheduleUpdate(JobHandle) and complete it. Failing to do could leave the remote peer unaware that the connection has been closed (however it will time out on its own after a while).
Declaration
public void Disconnect(NetworkConnection connection)
Parameters
Type | Name | Description |
---|---|---|
NetworkConnection | connection | Connection to close. |
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
Dispose()
Declaration
public void Dispose()
Implements
EndSend(DataStreamWriter)
Enqueue a send operation for the data in the given DataStreamWriter, which must have been obtained by a prior call to BeginSend(NetworkPipeline, NetworkConnection, out DataStreamWriter, Int32).
Declaration
public int EndSend(DataStreamWriter writer)
Parameters
Type | Name | Description |
---|---|---|
DataStreamWriter | writer | DataStreamWriter to send. |
Returns
Type | Description |
---|---|
Int32 | The number of bytes to be sent on success, a negative value on error. |
Remarks
This method doesn't actually send anything on the wire. It simply enqueues the send operation, which will be performed in the next ScheduleFlushSend(JobHandle) or ScheduleUpdate(JobHandle) job.
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
GetConnectionState(NetworkConnection)
Get the current state of the given connection.
Declaration
public NetworkConnection.State GetConnectionState(NetworkConnection connection)
Parameters
Type | Name | Description |
---|---|---|
NetworkConnection | connection | Connection to get the state of. |
Returns
Type | Description |
---|---|
NetworkConnection.State | State of the connection. |
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
GetDriver(Int32)
Get a NetworkDriver previously added with AddDriver(NetworkDriver).
Declaration
public NetworkDriver GetDriver(int id)
Parameters
Type | Name | Description |
---|---|---|
Int32 | id | ID of the driver as returned by AddDriver(NetworkDriver). |
Returns
Type | Description |
---|---|
NetworkDriver | The NetworkDriver referred to by |
Remarks
This method is provided as an escape hatch for use cases not covered by the
MultiNetworkDriver
API. Using this method to perform operations on a driver that
could be performed through MultiNetworkDriver
is likely to result in errors or
corrupted state.
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
GetDriverForConnection(NetworkConnection)
Get the NetworkDriver associated with the given connection. The connection
must have been obtained from the MultiNetworkDriver
before.
Declaration
public NetworkDriver GetDriverForConnection(NetworkConnection connection)
Parameters
Type | Name | Description |
---|---|---|
NetworkConnection | connection | Connection to get the driver of. |
Returns
Type | Description |
---|---|
NetworkDriver | The NetworkDriver associated to |
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
GetRemoteEndpoint(NetworkConnection)
Get the remote endpoint of a connection (the endpoint used to reach the remote peer on the connection).
Declaration
public NetworkEndpoint GetRemoteEndpoint(NetworkConnection connection)
Parameters
Type | Name | Description |
---|---|---|
NetworkConnection | connection | Connection to get the endpoint of. |
Returns
Type | Description |
---|---|
NetworkEndpoint | The remote endpoint of the connection. |
Remarks
The returned value should not be assumed to be constant for a given connection, as it is possible for remote peers to change address during the course of a session (e.g. if a mobile client changes IP address because they're hopping between cell towers).
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
PopEvent(out NetworkConnection, out DataStreamReader)
Pops the next event from the event queue, Empty will be returned if there are no more events to pop.
Declaration
public NetworkEvent.Type PopEvent(out NetworkConnection connection, out DataStreamReader reader)
Parameters
Type | Name | Description |
---|---|---|
NetworkConnection | connection | Connection on which the event occured. |
DataStreamReader | reader | DataStreamReader from which the event data (e.g. payload) can be read from. |
Returns
Type | Description |
---|---|
NetworkEvent.Type | The type of the event popped. |
Remarks
The reader
obtained from this method will contain different things for different
event types. For Data, it contains the actual received
payload. For Disconnect, it contains a single byte
identifying the reason for the disconnection (see DisconnectReason).
For other event types, it contains nothing.
PopEvent(out NetworkConnection, out DataStreamReader, out NetworkPipeline)
Pops the next event from the event queue, Empty will be returned if there are no more events to pop.
Declaration
public NetworkEvent.Type PopEvent(out NetworkConnection connection, out DataStreamReader reader, out NetworkPipeline pipe)
Parameters
Type | Name | Description |
---|---|---|
NetworkConnection | connection | Connection on which the event occured. |
DataStreamReader | reader | DataStreamReader from which the event data (e.g. payload) can be read from. |
NetworkPipeline | pipe | Pipeline on which the data event was received. |
Returns
Type | Description |
---|---|
NetworkEvent.Type | The type of the event popped. |
Remarks
The reader
obtained from this method will contain different things for different
event types. For Data, it contains the actual received
payload. For Disconnect, it contains a single byte
identifying the reason for the disconnection (see DisconnectReason).
For other event types, it contains nothing.
PopEventForConnection(NetworkConnection, out DataStreamReader)
Pops the next event from the event queue for the given connection, Empty will be returned if there are no more events.
Declaration
public NetworkEvent.Type PopEventForConnection(NetworkConnection connection, out DataStreamReader reader)
Parameters
Type | Name | Description |
---|---|---|
NetworkConnection | connection | Connection for which to pop the event. |
DataStreamReader | reader | DataStreamReader from which the event data (e.g. payload) can be read from. |
Returns
Type | Description |
---|---|
NetworkEvent.Type | The type of the event popped. |
Remarks
The reader
obtained from this method will contain different things for different
event types. For Data, it contains the actual received
payload. For Disconnect, it contains a single byte
identifying the reason for the disconnection (see DisconnectReason).
For other event types, it contains nothing.
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
PopEventForConnection(NetworkConnection, out DataStreamReader, out NetworkPipeline)
Pops the next event from the event queue for the given connection, Empty will be returned if there are no more events.
Declaration
public NetworkEvent.Type PopEventForConnection(NetworkConnection connection, out DataStreamReader reader, out NetworkPipeline pipe)
Parameters
Type | Name | Description |
---|---|---|
NetworkConnection | connection | Connection for which to pop the event. |
DataStreamReader | reader | DataStreamReader from which the event data (e.g. payload) can be read from. |
NetworkPipeline | pipe | Pipeline on which the data event was received. |
Returns
Type | Description |
---|---|
NetworkEvent.Type | The type of the event popped. |
Remarks
The reader
obtained from this method will contain different things for different
event types. For Data, it contains the actual received
payload. For Disconnect, it contains a single byte
identifying the reason for the disconnection (see DisconnectReason).
For other event types, it contains nothing.
Exceptions
Type | Condition |
---|---|
ArgumentException | If |
RegisterPipelineStage<T>(T)
Register a custom pipeline stage.
Declaration
public void RegisterPipelineStage<T>(T stage)
where T : struct, INetworkPipelineStage
Parameters
Type | Name | Description |
---|---|---|
T | stage | An instance of the pipeline stage. |
Type Parameters
Name | Description |
---|---|
T | Type of the pipeline stage (must be unmanaged). |
Remarks
Can only be called before a driver is bound (see Bind(NetworkEndpoint)).
Note that the default pipeline stages (FragmentationPipelineStage, ReliableSequencedPipelineStage, UnreliableSequencedPipelineStage, and SimulatorPipelineStage) don't need to be registered. Registering a pipeline stage is only required for custom ones.
Exceptions
Type | Condition |
---|---|
InvalidOperationException | If the driver is not created or bound. Note that this is only thrown if safety checks are enabled (i.e. in the editor). Otherwise the pipeline is registered anyway (with likely erroneous behavior down the line). |
ScheduleFlushSend(JobHandle)
Schedule a send job. This job is basically a subset of the update job (see ScheduleUpdate(JobHandle)) and only takes care of sending packets queued with EndSend(DataStreamWriter). It should be lightweight enough to schedule multiple times per tick to improve latency if there's a significant amount of packets being sent.
Declaration
public JobHandle ScheduleFlushSend(JobHandle dependency = default(JobHandle))
Parameters
Type | Name | Description |
---|---|---|
JobHandle | dependency | Job to depend on. |
Returns
Type | Description |
---|---|
JobHandle | Handle to the send job. |
ScheduleUpdate(JobHandle)
Schedule an update job. This job will process incoming packets and check timeouts (queueing up the relevant events to be consumed by PopEvent(out NetworkConnection, out DataStreamReader) and Accept()) and will send any packets queued with EndSend(DataStreamWriter). This job should generally be scheduled once per tick.
Declaration
public JobHandle ScheduleUpdate(JobHandle dependency = default(JobHandle))
Parameters
Type | Name | Description |
---|---|---|
JobHandle | dependency | Job to depend on. |
Returns
Type | Description |
---|---|
JobHandle | Handle to the update job. |
ToConcurrent()
Create a NetworkDriver.Concurrent copy of the NetworkDriver
.
Declaration
public MultiNetworkDriver.Concurrent ToConcurrent()
Returns
Type | Description |
---|---|
MultiNetworkDriver.Concurrent | A NetworkDriver.Concurrent instance for the driver. |