RiptideNetworking / Riptide

Lightweight C# networking solution for multiplayer games.
https://riptide.tomweiland.net
MIT License
1.06k stars 141 forks source link

Serialisation Bug #124

Closed eeetem closed 6 months ago

eeetem commented 6 months ago

After migrating to 2.1.1 version from 2.0.0 there's an issue when it comes to deserialising integers

for (int i = 0; i < 10; i++)
{
    Console.WriteLine(i);
    Data d = new Data();
    d.str = Random.Shared.Next().ToString();
    d.num = Random.Shared.Next();

    Message message = Message.Create();
    message.AddSerializable(d);
    var d2 = message.GetSerializable<Data>();

    message.Release();

    if (!d.Equals(d2))
    {
        Console.WriteLine(d);
        Console.WriteLine(d2);
        throw new Exception("not equal!");
    }
}

public struct Data : IMessageSerializable
{
    public int num = -1;
    public string str = "";

    public Data()
    {
    }

    public override string ToString()
    {
        return $"{nameof(num)}: {num}, {nameof(str)}: {str}";
    }

    public void Serialize(Message message)
    {
        message.AddString(str);
        message.AddInt(num);

    }

    public void Deserialize(Message message)
    {
        str = message.GetString();
        num = message.GetInt();
    }

}

This code works perfectly fine on 2.0.0. while running it on 2.1.1 on the second iteration of the loop for whatever reason the integer gets deserialsed incorrectly.

The issue appears to be related to message pooling since removing message.release() "fixes" the issue.

tom-weiland commented 6 months ago

This is happening because AddBytes (which AddString calls internally) doesn't properly reset data segments before writing when writeBit % BitsPerByte == 0.