Deserializing Protobuf c# from wire

505 Views Asked by At

I am using the protobuf google implementation for c#.

The story so far..I have a server in c++ and clients in c# and the talk via protobuf messages with TCP.

On the client side, I retrieve the buffers returned from the tcpClient.BeginReceive via the callback provided and append them (so I guess it is cleared from the netstream junk). Then on a worker thread, I try to deserialize the messages.

On the server side the serialization code is:

google::protobuf::uint32 msgSize = msg->ByteSize();
int prefix_length = sizeof(msgSize);
int buffer_length = msgSize + prefix_length;

google::protobuf::uint8 buffer[buffer_length];
google::protobuf::io::ArrayoutputStream array_output(buffer, buffer_length, msgSize);
google::protobuf::io::CodedOutputStream coded_output(&array_output);

coded_output.WriteVarint32(msgSize);
msg->SerializeToCodedStream(&coded_output);

//Send to socket
mSendBuffer.Write(buffer, buffer_length);

On the client I read each chunk using CodedInputStream, read the first number and dispatch the prefix+the msg it contains for deserialization

Figuring out the length:

using (var input = new CodedInputStream(chunk))
{
   int len = input.ReadInt32();
   int requiredLength = len + input.Position; //(we re sure each time the codedInput starts from the beginning)
   byte[] read = await AccumulateResources(requiredLength, chunk);
   byte[] msg = new byte[requiredLength];
   Buffer.BlockCopy(read, 0, msg , 0 , requiredLength);
   Dispatch(msg);
} 

Deserialization:

using (var ms = new MemoryStream(buff))
{
    ServerMessageFrame msg = null;
    try
    {
       msg = ServerMessageFrame.Parser.ParseDelimitedFrom(ms);
    }
    catch(Exception e)
    {
      Logger.Write(conn.clntPrefx + "  " + e.ToString());
    }
    //Use the message
 }

The error Messages I receive are:

1)System.InvalidOperationExeption: Wire Type is invalid

2)Protocol message contained invalid tag (zero).

The communication is correct at the beginning and it desyncs at some point, from where it breaks (until I read another msg which starts with a prefixed value aka is not a partial message) My question is the de/serialization sound or I am missing the mark completely like there is something that I don't account for at all.

0

There are 0 best solutions below