Nanopb is an ANSI-C library for encoding and decoding messages in Google’s Protocol Buffers format with minimal requirements for RAM and code space. It is primarily suitable for 32-bit microcontrollers.
This documentation applies for nanopb 0.4.0 and later versions. For documentation of older releases, see here.
For the runtime program, you always need pb.h
for type
declarations and pb_common.h/c
for base functions.
Depending on whether you want to encode, decode, or both, you also need
pb_encode.h/c
or pb_decode.h/c
.
The high-level encoding and decoding functions take a pointer to
pb_msgdesc_t
structure, which describes the fields of a
message structure. Usually you want these autogenerated from a
.proto
file. The tool script
nanopb_generator.py
accomplishes this.
So a typical project might include these files:
Features
Limitations
sort_by_tag
setting.)For starters, consider this simple message:
message Example {
required int32 value = 1;
}
Save this in message.proto
and compile it:
:~$ python nanopb/generator/nanopb_generator.py message.proto user@host
You should now have in message.pb.h
:
typedef struct {
int32_t value;
} Example;
extern const pb_msgdesc_t Example_msg;
#define Example_fields &Example_msg
Then you have to include the nanopb headers and the generated header:
#include <pb_encode.h>
#include "message.pb.h"
Now in your main program do this to encode a message:
= {42};
Example mymessage uint8_t buffer[10];
= pb_ostream_from_buffer(buffer, sizeof(buffer));
pb_ostream_t stream (&stream, Example_fields, &mymessage); pb_encode
After that, buffer will contain the encoded message. The number of
bytes in the message is stored in stream.bytes_written
. You
can feed the message to
protoc --decode=Example message.proto
to verify its
validity.
For a complete example of the simple case, see examples/simple/simple.c. For a more complex example with network interface, see the examples/network_server subdirectory.
Nanopb should compile with most ansi-C compatible compilers. It however requires a few header files to be available:
string.h
, with these functions: strlen
,
memcpy
, memset
stdint.h
, for definitions of int32_t
etc.stddef.h
, for definition of size_t
stdbool.h
, for definition of bool
limits.h
, for definition of CHAR_BIT
If these header files do not come with your compiler, you can use the
file extra/pb_syshdr.h
instead. It contains an example of
how to provide the dependencies. You may have to edit it a bit to suit
your custom platform.
To use the pb_syshdr.h, define PB_SYSTEM_HEADER
as
"pb_syshdr.h"
(including the quotes). Similarly, you can
provide a custom include file, which should provide all the dependencies
listed above.
Extensive unittests and test cases are included under the
tests
folder.
To build the tests, you will need the scons build system. The tests should be runnable on most platforms. Windows and Linux builds are regularly tested. The tests also support embedded targets: STM32 (ARM Cortex-M) and AVR builds are regularly tested.
In addition to the build system, you will also need a working Google
Protocol Buffers protoc
compiler, and the Python bindings
for Protocol Buffers.
Easiest way to install dependencies is to use the Python package manager pip, which works on all platforms supported by Python:
-tools pip3 install scons protobuf grpcio