Skip to content

Commit

Permalink
perf: Pack small 32 bit negatives efficiently
Browse files Browse the repository at this point in the history
  • Loading branch information
paulpach committed Mar 31, 2019
1 parent 3ec7f6c commit 480af1a
Show file tree
Hide file tree
Showing 8 changed files with 76 additions and 22 deletions.
4 changes: 2 additions & 2 deletions Assets/Mirror/Components/NetworkAnimator.cs
Original file line number Diff line number Diff line change
Expand Up @@ -229,7 +229,7 @@ bool WriteParameters(NetworkWriter writer)
if (par.type == AnimatorControllerParameterType.Int)
{
int newIntValue = animator.GetInteger(par.nameHash);
writer.WritePackedUInt32((uint)newIntValue);
writer.WritePackedInt32(newIntValue);
}
else if (par.type == AnimatorControllerParameterType.Float)
{
Expand All @@ -256,7 +256,7 @@ void ReadParameters(NetworkReader reader)
AnimatorControllerParameter par = parameters[i];
if (par.type == AnimatorControllerParameterType.Int)
{
int newIntValue = (int)reader.ReadPackedUInt32();
int newIntValue = reader.ReadPackedInt32();
animator.SetInteger(par.nameHash, newIntValue);
}
else if (par.type == AnimatorControllerParameterType.Float)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -462,7 +462,7 @@ void DeserializeField(FieldDefinition syncVar, ILProcessor serWorker, MethodDefi

// read id and store in a local variable
serWorker.Append(serWorker.Create(OpCodes.Ldarg_1));
serWorker.Append(serWorker.Create(OpCodes.Call, Weaver.NetworkReaderReadPacked32));
serWorker.Append(serWorker.Create(OpCodes.Call, Weaver.NetworkReaderReadPackedUInt32));
serWorker.Append(serWorker.Create(OpCodes.Stloc, tmpValue));

if (foundMethod != null)
Expand Down
20 changes: 12 additions & 8 deletions Assets/Mirror/Editor/Weaver/Weaver.cs
Original file line number Diff line number Diff line change
Expand Up @@ -101,10 +101,12 @@ class Weaver
public static MethodReference NetworkServerGetLocalClientActive;
public static MethodReference NetworkClientGetActive;
public static MethodReference UBehaviourIsServer;
public static MethodReference NetworkReaderReadPacked32;
public static MethodReference NetworkReaderReadPackedUInt32;
public static MethodReference NetworkReaderReadPackedInt32;
public static MethodReference NetworkReaderReadPacked64;
public static MethodReference NetworkReaderReadByte;
public static MethodReference NetworkWriterWritePacked32;
public static MethodReference NetworkWriterWritePackedUInt32;
public static MethodReference NetworkWriterWritePackedInt32;
public static MethodReference NetworkWriterWritePacked64;

public static MethodReference NetworkReadUInt16;
Expand Down Expand Up @@ -1101,11 +1103,13 @@ static void SetupTargetTypes()
NetworkWriterWriteInt32 = Resolvers.ResolveMethodWithArg(NetworkWriterType, CurrentAssembly, "Write", int32Type);
NetworkWriterWriteInt16 = Resolvers.ResolveMethodWithArg(NetworkWriterType, CurrentAssembly, "Write", int16Type);

NetworkReaderReadPacked32 = Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadPackedUInt32");
NetworkReaderReadPackedUInt32 = Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadPackedUInt32");
NetworkReaderReadPackedInt32 = Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadPackedInt32");
NetworkReaderReadPacked64 = Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadPackedUInt64");
NetworkReaderReadByte = Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadByte");

NetworkWriterWritePacked32 = Resolvers.ResolveMethod(NetworkWriterType, CurrentAssembly, "WritePackedUInt32");
NetworkWriterWritePackedUInt32 = Resolvers.ResolveMethod(NetworkWriterType, CurrentAssembly, "WritePackedUInt32");
NetworkWriterWritePackedInt32 = Resolvers.ResolveMethod(NetworkWriterType, CurrentAssembly, "WritePackedInt32");
NetworkWriterWritePacked64 = Resolvers.ResolveMethod(NetworkWriterType, CurrentAssembly, "WritePackedUInt64");

NetworkReadUInt16 = Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadUInt16");
Expand Down Expand Up @@ -1182,8 +1186,8 @@ static void SetupReadFunctions()
{ stringType.FullName, Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadString") },
{ int64Type.FullName, NetworkReaderReadPacked64 },
{ uint64Type.FullName, NetworkReaderReadPacked64 },
{ int32Type.FullName, NetworkReaderReadPacked32 },
{ uint32Type.FullName, NetworkReaderReadPacked32 },
{ int32Type.FullName, NetworkReaderReadPackedInt32 },
{ uint32Type.FullName, NetworkReaderReadPackedUInt32 },
{ int16Type.FullName, Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadInt16") },
{ uint16Type.FullName, Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadUInt16") },
{ byteType.FullName, Resolvers.ResolveMethod(NetworkReaderType, CurrentAssembly, "ReadByte") },
Expand Down Expand Up @@ -1220,8 +1224,8 @@ static void SetupWriteFunctions()
{ stringType.FullName, Resolvers.ResolveMethodWithArg(NetworkWriterType, CurrentAssembly, "Write", stringType) },
{ int64Type.FullName, NetworkWriterWritePacked64 },
{ uint64Type.FullName, NetworkWriterWritePacked64 },
{ int32Type.FullName, NetworkWriterWritePacked32 },
{ uint32Type.FullName, NetworkWriterWritePacked32 },
{ int32Type.FullName, NetworkWriterWritePackedInt32 },
{ uint32Type.FullName, NetworkWriterWritePackedUInt32 },
{ int16Type.FullName, Resolvers.ResolveMethodWithArg(NetworkWriterType, CurrentAssembly, "Write", int16Type) },
{ uint16Type.FullName, Resolvers.ResolveMethodWithArg(NetworkWriterType, CurrentAssembly, "Write", uint16Type) },
{ byteType.FullName, Resolvers.ResolveMethodWithArg(NetworkWriterType, CurrentAssembly, "Write", byteType) },
Expand Down
4 changes: 2 additions & 2 deletions Assets/Mirror/Runtime/Messages.cs
Original file line number Diff line number Diff line change
Expand Up @@ -99,12 +99,12 @@ public IntegerMessage(int v)

public override void Deserialize(NetworkReader reader)
{
value = (int)reader.ReadPackedUInt32();
value = reader.ReadPackedInt32();
}

public override void Serialize(NetworkWriter writer)
{
writer.WritePackedUInt32((uint)value);
writer.WritePackedInt32(value);
}
}

Expand Down
11 changes: 9 additions & 2 deletions Assets/Mirror/Runtime/NetworkReader.cs
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,13 @@ public byte[] ReadBytesAndSize()
return null;
}

// zigzag decoding https://gist.github.com/mfuerstenau/ba870a29e16536fdbaba
public int ReadPackedInt32()
{
uint data = ReadPackedUInt32();
return (int)((data >> 1) ^ -(data & 1));
}

// http://sqlite.org/src4/doc/trunk/www/varint.wiki
// NOTE: big endian.
public uint ReadPackedUInt32()
Expand Down Expand Up @@ -145,12 +152,12 @@ public Vector4 ReadVector4()

public Vector2Int ReadVector2Int()
{
return new Vector2Int((int)ReadPackedUInt32(), (int)ReadPackedUInt32());
return new Vector2Int(ReadPackedInt32(), ReadPackedInt32());
}

public Vector3Int ReadVector3Int()
{
return new Vector3Int((int)ReadPackedUInt32(), (int)ReadPackedUInt32(), (int)ReadPackedUInt32());
return new Vector3Int(ReadPackedInt32(), ReadPackedInt32(), ReadPackedInt32());
}

public Color ReadColor()
Expand Down
17 changes: 12 additions & 5 deletions Assets/Mirror/Runtime/NetworkWriter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,13 @@ public void WriteBytesAndSize(byte[] buffer)
WriteBytesAndSize(buffer, 0, buffer != null ? buffer.Length : 0);
}

// zigzag encoding https://gist.github.com/mfuerstenau/ba870a29e16536fdbaba
public void WritePackedInt32(int i)
{
uint zigzagged = (uint)((i >> 31) ^ (i << 1));
WritePackedUInt32(zigzagged);
}

// http://sqlite.org/src4/doc/trunk/www/varint.wiki
public void WritePackedUInt32(uint value)
{
Expand Down Expand Up @@ -216,15 +223,15 @@ public void Write(Vector4 value)

public void Write(Vector2Int value)
{
WritePackedUInt32((uint)value.x);
WritePackedUInt32((uint)value.y);
WritePackedInt32(value.x);
WritePackedInt32(value.y);
}

public void Write(Vector3Int value)
{
WritePackedUInt32((uint)value.x);
WritePackedUInt32((uint)value.y);
WritePackedUInt32((uint)value.z);
WritePackedInt32(value.x);
WritePackedInt32(value.y);
WritePackedInt32(value.z);
}

public void Write(Color value)
Expand Down
4 changes: 2 additions & 2 deletions Assets/Mirror/Runtime/SyncList.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,8 @@ public class SyncListFloat : SyncList<float>

public class SyncListInt : SyncList<int>
{
protected override void SerializeItem(NetworkWriter writer, int item) => writer.WritePackedUInt32((uint)item);
protected override int DeserializeItem(NetworkReader reader) => (int)reader.ReadPackedUInt32();
protected override void SerializeItem(NetworkWriter writer, int item) => writer.WritePackedInt32(item);
protected override int DeserializeItem(NetworkReader reader) => reader.ReadPackedInt32();
}

public class SyncListUInt : SyncList<uint>
Expand Down
36 changes: 36 additions & 0 deletions Assets/Mirror/Tests/NetworkWriterTest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,42 @@ public void TestPackedUInt32()
Assert.That(reader.ReadPackedUInt32(), Is.EqualTo(uint.MaxValue));
}

[Test]
public void TestPackedInt32()
{
NetworkWriter writer = new NetworkWriter();
writer.WritePackedInt32(0);
writer.WritePackedInt32(234);
writer.WritePackedInt32(2284);
writer.WritePackedInt32(67821);
writer.WritePackedInt32(16777210);
writer.WritePackedInt32(16777219);
writer.WritePackedInt32(int.MaxValue);
writer.WritePackedInt32(-1);
writer.WritePackedInt32(-234);
writer.WritePackedInt32(-2284);
writer.WritePackedInt32(-67821);
writer.WritePackedInt32(-16777210);
writer.WritePackedInt32(-16777219);
writer.WritePackedInt32(int.MinValue);

NetworkReader reader = new NetworkReader(writer.ToArray());
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(0));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(234));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(2284));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(67821));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(16777210));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(16777219));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(int.MaxValue));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(-1));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(-234));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(-2284));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(-67821));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(-16777210));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(-16777219));
Assert.That(reader.ReadPackedInt32(), Is.EqualTo(int.MinValue));
}

[Test]
public void TestPackedUInt64()
{
Expand Down

0 comments on commit 480af1a

Please sign in to comment.