'Google.Protobuf.InvalidProtocolBufferException: Protocol message contained an invalid tag (zero)

I have a problem with my school project, i use Protobuf library but i have the following error:

Google.Protobuf.InvalidProtocolBufferException" Protocol message contained an invalid tag (zero).

My protocol message wrapper is:

syntax = "proto3";
package CardGameGUI.Network.Protocol.Message;

message WrapperMessage {
enum MessageType {
    HELLO_MESSAGE = 0;
    JOIN_ROOM_MESSAGE = 1;
    JOIN_ROOM_RESPONSE_MESSAGE = 2;
}

MessageType type = 1;
bytes       payload = 2;
}

I use this to send a message:

    public void SendObject<T>(Protocol.Message.WrapperMessage.Types.MessageType type, T messageObject)
    {
        byte[] message;

        // Serialize message
        using (var stream = new MemoryStream())
        {
            ((IMessage)messageObject).WriteTo(stream);

            message = stream.GetBuffer();
        }

        byte[] wrapper = new Protocol.Message.WrapperMessage{Type = type, Payload = Google.Protobuf.ByteString.CopyFrom(message)}.ToByteArray();

        Connection.SendObject<byte[]>("ByteMessage", wrapper);
    }

And my server handler:

private void IncommingMessageHandler(PacketHeader header, Connection connection, byte[] message)
    {
        Protocol.Message.WrapperMessage wrapper = Protocol.Message.WrapperMessage.Parser.ParseFrom(message);

        switch (wrapper.Type)
        {
            case Protocol.Message.WrapperMessage.Types.MessageType.HelloMessage:
                GetClient(connection.ConnectionInfo.NetworkIdentifier).MessageHandler(Protocol.Message.HelloMessage.Parser.ParseFrom(wrapper.Payload.ToByteArray()));

                break;
        }
    }

The wrapper message is perfectly unserialized, and type is correctly matched, but at the treatment of my Payload, the exception pops.

Do i do something bad?

Edit: a small screen of the message Payload Payload



Solution 1:[1]

i encounter this problem in this case because my serialize bytestream loss the varint lenth

such as if i serialize a "Person.proto" message which have 672 bytes if i deserialize the 672 bytes will encounter the error

the solve strategy is that add the varint len in the 672bytes so youcan get a 674bytes stream

the extra amount data is the "varint" code for 672, which is 160,5

you can get the varint bytes by the function

public static byte[] VarInt(int value)
{
    //data len
    List<byte> varIntBuffer = new List<byte>();
    int index = 0;
    while (true)
    {
        if ((value & ~0x7f) == 0)
        {
            varIntBuffer.Add((byte)(value & 0x7f));
            break;
        }
        else
        {
            varIntBuffer.Add((byte)((value & 0x7f) | 0x80));
            value = value >> 7;
        }
        index++;
    }
    return varIntBuffer.ToArray();
}

Solution 2:[2]

I had this same issue when attempting to deserialize a byte array which had been initialized to a fixed size but there was a bug which meant I was not populating the array with proto bytes (so the byte array was populated with zeros when I was attempting to deserialize).

It turns out that I was reading bytes from a JMS BytesMessage twice in a test case but was not calling BytesMessage.reset() before the second read.

I'm guessing you could get a similar bug if attempting to read from an InputStream twice without calling reset()

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 enchanter
Solution 2