I am storing Protobufs inside of some non-volatile memory in order to save configuration information. I am using NanoPB to decode/encode them. Since I do not know how large the encoded Protobufs are, when I go to grab a serialized proto from memory and decode, I just grab the maximum number of bytes that the enocded protobuf could be, even if it takes up fewer bytes.
My question is: do I have to store some data describing how many bytes the protobuf is so that I can decode properly?
Or is there a way for me to determine that myself if I 0-pad the serialized buffer or use some other method. As it stands, NanoPB is failing to decode the bytes I am giving it, most likely because there is some garbage data after the end of the encoded proto and I have no way of telling how long the serialized data is.
Yes, the end of protobuf messages has to be indicated somehow, as the format is not self-delimiting.
Nanopb provides two built-in methods for this:
pb_encode_nullterminated()
andpb_decode_nullterminated()
, which append a0x00
byte to the encoded data and detect it when decoding. It is a neat way to do it, but does not have a widespread support in other protobuf libraries. Therefore it is mostly useful when nanopb is used for both encoding and decoding.pb_encode_delimited()
andpb_decode_delimited()
, which prepend the size before the message. This is supported by several other protobuf libraries also. A downside is that the encoder has to first determine the length of the message before encoding it, which currently gives a small performance penalty in nanopb.One can also use custom methods, such as storing the message length at a separate memory location.