diff --git a/Protocol.md b/Protocol.md index 49083c1..ff3b92b 100644 --- a/Protocol.md +++ b/Protocol.md @@ -1 +1,99 @@ -Protocol wiki \ No newline at end of file +# Protocol + +The protocol used is based on **TCP** connections for maximum security. +At the moment, it doesn't use **TLS** but plan to in a near future. + +## Packet + +A simple packet looks like this: + +| Command | Argument 1 | Argument 2 | +| :-----: | :--------: | :--------: | +| PING | Hello | World! | + +- **Command** - Always represent a single **uppercase** word as a command +- **Arguments** - Represent a **semicolon-delimited** list of arguments + +Since all is a string, it is represented as: + +```md +PING +Hello;World!\n +``` + +Notice the `\n` at the end, it is used to show the end of the packet. +So, in one line, the packet is: `PING\nHello;World!\n` + +## ID + +Since the broker need to know the destination of a packet, we add an id as an argument: + +| Command | Argument 1 | Argument 2 | Argument 3 | +| :-----: | :--------: | :--------: | :--------: | +| PING | ID | Hello | World! | + +- **ID** - a 64 bit unsigned integer + +Here is the string representation: + +```md +PING +ID;Hello;World!\n +``` + +The consequence is that the first argument is **always** used for the **ID** + +## Byte Representation + +A packet need to be sent as **bytes**, here are the rules to send a packet: + +- The first **4** bytes are the total byte length of the packet as a 32 bit unsigned integer +- The string representation of the packet is encoded in **UTF-8** + +We must send the byte-length since UTF-8 is variable in size, we can't send the characters count. + +A simple example to read a packet in C#: + +```cs +// _stream is a connected NetworkStream + +// Length +byte[] buffer = new byte[4]; +_stream.Read(buffer, 0, buffer.Length); + +uint length = BitConverter.ToUInt32(buffer, 0); + +// Data +buffer = new byte[length]; +_stream.Read(buffer, 0, buffer.Length); + +string[] packet = Encoding.UTF8.GetString(buffer).Split('\n'); + +// Parse +string command = packet[0]; +string[] arguments = packet[1].Split(';'); +``` + +And here an example to write a packet in C#: + +```cs +// _stream is a connected NetworkStream + +// Command +string command = "PING"; +uint id = "457545645"; +string argument1 = "Hello"; +string argument2 = "World!"; +string packet = command + "\n" + id.ToString() + ";" + argument1 + ";" + argument2 + "\n"; + +byte[] data = Encoding.UTF8.GetBytes(packet); // Convert to UTF-8 bytes + +_stream.Write(BitConverter.GetBytes(data.Length), 0, 4); // Send the length +_stream.Write(data, 0, data.Length); // Send the packet +``` + +## Commands + +Each command is described in a dedicated page + +- TODO \ No newline at end of file