Skip to content

🕷️ authoritative server protocol and .NET library for games using udp

Notifications You must be signed in to change notification settings

dcronqvist/Arachne

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

31 Commits
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

🕷️ Arachne .NET Tests

Protocol

The Arachne protocol is a simple protocol that allows for clients to connect to an authoritative server using some kind of identification, and will then allow the client and server to communicate with each other. This protocol is very simple and is primarily designed to be used in games, but could potentially be used in other applications as well.

It uses UDP for all communication and allows for 4 different ways of communication:

  • Unreliably, fastest way of communication, but packets can be lost.

  • Reliably, slower way of communication, but packets will never be lost.

No regard for order is taken for ANY packets sent, so the order of received packets is not guaranteed to be the same as the order of sent packets.

Protocol packets

The protocol consists of a few different packets, which are mostly used for connection intialization, and connection termination.

Protocol packet types and channels

The protocol uses 4 different channels and has 8 different packet types. Both the channel and packet type are specified as a single bit packed byte in the packet header. The channel is specified in the high 4 bits, and the packet type is specified in the low 4 bits.

The 4 different channels are:

Unreliable  = 0x00
Reliable    = 0x10

The 8 different packet types are:

Connection request              = 0x00
Connection challenge            = 0x01
Connection challenge response   = 0x02
Connection response             = 0x03
Connection keep alive           = 0x04
Application data                = 0x05
Connection termination          = 0x06
Connection termination ack      = 0x07
Server info request             = 0x08
Server info response            = 0x09

So, a packet header with a first byte of 0x00 would be a Connection request packet on the Unreliable channel. A packet header with a first byte of 0x15 would be an Application data packet on the Reliable channel.

The entire packet header looks like the following:

[channel + packet type] (1 byte, high 4b = channel, low 4b = type)
[sequence number]       (8 bytes)
[sequence ack]          (8 bytes)
[ack bits]              (4 bytes)
...
[data]                  (variable length)

A total of 21 bytes of overhead is added to each packet, to allow for the Arachne protocol to function properly.

Connection initialization

There 2 different ways to allow for a connection to be established.

  • No authentication - This is the simplest way of connecting, and is used when the server does not require any kind of authentication from the client. The client will simply send a CR packet to the server, and the server will respond with a CRS packet either allowing or denying the connection.

  • With authentication - This is a more complex way of connecting, and is used when the server requires some kind of authentication from the client. The client will send a CR packet to the server, and the server will respond with a CH packet, which will contain a challenge for the client. The client will then respond with a CHR packet, which will contain the challenge response. The server will then respond with a CRS packet either allowing or denying the connection. The authentication method is up to the developer to implement, however, there are some examples provided if needed.

Connection Request (CR)

This packet is sent by the client to the server, and is used to request a connection to the server. The server will then respond with a Connection Response packet.

If the given protocol id and protocol version is not supported by the server, the server will respond with a CRS packet with response code 0x01 (unsupported protocol).

[header]            (21 bytes) (always sent on the Reliable channel)
...
[protocol id]       (4 bytes)
[protocol version]  (4 bytes)

Connection Challenge (CH)

This packet is sent by the server to the client, and is used to challenge the client to prove that it is allowed to connect. The client will then respond with a CHR packet.

The packet can contain anything that the developer so chooses, and it is up to the developer to implement this.

[header]            (21 bytes) (always sent on the Reliable channel)
...
[challenge length]  (4 bytes)
[challenge]         (variable length)

Connection Challenge Response (CHR)

This packet is sent by the client to the server, and is used to respond to the challenge that the server sent. The server will then respond with a CRS packet.

[header]            (21 bytes) (always sent on the Reliable channel)
...
[response length]   (4 bytes)
[response]          (variable length)

Connection Response (CRS)

This packet is sent by the server to the client, and is used to respond to a Connection Request packet. This response will contain a code that will indicate the outcome of the connection request.

[header]        (21 bytes) (always sent on the Reliable channel)
...
[response code] (1 byte)
[client id]     (8 bytes)

During connection packets

Connection Keep Alive (KA)

This packet is sent by the client to the server, and is used to keep the connection alive. The server will not respond to this packet, it is only for the server to know if the client is still alive and connected.

KA packets are sent every 5 seconds by default, but this can be changed by the developer.

If no KA packets are received from a connected client within a specified timeout, the server will consider the client to be disconnected and will remove the client from its list of connected clients.

[header] (21 bytes) (always sent on the Unreliable channel)
...
(no data, packet type enough)

Application Data (AD)

This packet can be sent by either the client or the server, and is used to send application data to the other party. The packet can contain any kind of data that the developer so chooses.

[header]        (21 bytes) (sent on whichever channel the developer chooses)
...
[data length]   (4 bytes)
[data]          (variable length)

Connection termination

Connection Termination (CT)

This packet is sent by either the client or the server, and is used to terminate the connection. The packet can contain a reason for the termination. The other party should then respond with a CTA packet, to acknowledge the termination.

[header]        (21 bytes) (always sent on the Reliable channel)
...
[reason length] (4 bytes)
[reason string] (variable length, UTF-8 encoded)

Connection Termination Acknowledgement (CTA)

This packet is sent by either the client or the server, and is used to acknowledge the termination of the connection.

[header] (21 bytes) (always sent on the Reliable channel)
...
(no data, packet type enough)

Server info

Server Info Request (SIR)

This packet is sent by the client to the server, and is used to request information about the server. The server will then respond with a SIRS packet.

[header] (21 bytes) (always sent on the Unreliable channel)
...
(no data, packet type enough)

Server Info Response (SIRS)

This packet is sent by the server to the client, and is used to respond to a SIR packet. This response will contain information about the server.

[header]        (21 bytes) (always sent on the Unreliable channel)
...
[info]          (variable length, raw bytes)

The info field can contain any kind of data that the developer so chooses, and it is up to the developer to implement this, using an IServerInfoProvider implementation.

Releases

No releases published

Packages

No packages published

Languages