Add compile-time option PB_BUFFER_ONLY.
This allows slight optimizations if only memory buffer support (as opposed to stream callbacks) is wanted. On ARM difference is -12% execution time, -4% code size when enabled.
This commit is contained in:
@@ -22,6 +22,8 @@ PB_FIELD_32BIT Add support for tag numbers > 65535 and fields la
|
|||||||
Increases code size 9 bytes per each field. Compiler error will tell if you need this.
|
Increases code size 9 bytes per each field. Compiler error will tell if you need this.
|
||||||
PB_NO_ERRMSG Disables the support for error messages; only error information is the true/false return value.
|
PB_NO_ERRMSG Disables the support for error messages; only error information is the true/false return value.
|
||||||
Decreases the code size by a few hundred bytes.
|
Decreases the code size by a few hundred bytes.
|
||||||
|
PB_BUFFER_ONLY Disables the support for custom streams. Only supports encoding to memory buffers.
|
||||||
|
Speeds up execution and decreases code size slightly.
|
||||||
============================ ================================================================================================
|
============================ ================================================================================================
|
||||||
|
|
||||||
The PB_MAX_REQUIRED_FIELDS, PB_FIELD_16BIT and PB_FIELD_32BIT settings allow raising some datatype limits to suit larger messages.
|
The PB_MAX_REQUIRED_FIELDS, PB_FIELD_16BIT and PB_FIELD_32BIT settings allow raising some datatype limits to suit larger messages.
|
||||||
|
|||||||
11
pb_decode.c
11
pb_decode.c
@@ -52,6 +52,7 @@ static bool checkreturn buf_read(pb_istream_t *stream, uint8_t *buf, size_t coun
|
|||||||
|
|
||||||
bool checkreturn pb_read(pb_istream_t *stream, uint8_t *buf, size_t count)
|
bool checkreturn pb_read(pb_istream_t *stream, uint8_t *buf, size_t count)
|
||||||
{
|
{
|
||||||
|
#ifndef PB_BUFFER_ONLY
|
||||||
if (buf == NULL && stream->callback != buf_read)
|
if (buf == NULL && stream->callback != buf_read)
|
||||||
{
|
{
|
||||||
/* Skip input bytes */
|
/* Skip input bytes */
|
||||||
@@ -66,12 +67,18 @@ bool checkreturn pb_read(pb_istream_t *stream, uint8_t *buf, size_t count)
|
|||||||
|
|
||||||
return pb_read(stream, tmp, count);
|
return pb_read(stream, tmp, count);
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
if (stream->bytes_left < count)
|
if (stream->bytes_left < count)
|
||||||
PB_RETURN_ERROR(stream, "end-of-stream");
|
PB_RETURN_ERROR(stream, "end-of-stream");
|
||||||
|
|
||||||
|
#ifndef PB_BUFFER_ONLY
|
||||||
if (!stream->callback(stream, buf, count))
|
if (!stream->callback(stream, buf, count))
|
||||||
PB_RETURN_ERROR(stream, "io error");
|
PB_RETURN_ERROR(stream, "io error");
|
||||||
|
#else
|
||||||
|
if (!buf_read(stream, buf, count))
|
||||||
|
return false;
|
||||||
|
#endif
|
||||||
|
|
||||||
stream->bytes_left -= count;
|
stream->bytes_left -= count;
|
||||||
return true;
|
return true;
|
||||||
@@ -80,7 +87,11 @@ bool checkreturn pb_read(pb_istream_t *stream, uint8_t *buf, size_t count)
|
|||||||
pb_istream_t pb_istream_from_buffer(uint8_t *buf, size_t bufsize)
|
pb_istream_t pb_istream_from_buffer(uint8_t *buf, size_t bufsize)
|
||||||
{
|
{
|
||||||
pb_istream_t stream;
|
pb_istream_t stream;
|
||||||
|
#ifdef PB_BUFFER_ONLY
|
||||||
|
stream.callback = NULL;
|
||||||
|
#else
|
||||||
stream.callback = &buf_read;
|
stream.callback = &buf_read;
|
||||||
|
#endif
|
||||||
stream.state = buf;
|
stream.state = buf;
|
||||||
stream.bytes_left = bufsize;
|
stream.bytes_left = bufsize;
|
||||||
#ifndef PB_NO_ERRMSG
|
#ifndef PB_NO_ERRMSG
|
||||||
|
|||||||
@@ -32,7 +32,16 @@ extern "C" {
|
|||||||
*/
|
*/
|
||||||
struct _pb_istream_t
|
struct _pb_istream_t
|
||||||
{
|
{
|
||||||
|
#ifdef PB_BUFFER_ONLY
|
||||||
|
/* Callback pointer is not used in buffer-only configuration.
|
||||||
|
* Having an int pointer here allows binary compatibility but
|
||||||
|
* gives an error if someone tries to assign callback function.
|
||||||
|
*/
|
||||||
|
int *callback;
|
||||||
|
#else
|
||||||
bool (*callback)(pb_istream_t *stream, uint8_t *buf, size_t count);
|
bool (*callback)(pb_istream_t *stream, uint8_t *buf, size_t count);
|
||||||
|
#endif
|
||||||
|
|
||||||
void *state; /* Free field for use by callback implementation */
|
void *state; /* Free field for use by callback implementation */
|
||||||
size_t bytes_left;
|
size_t bytes_left;
|
||||||
|
|
||||||
|
|||||||
11
pb_encode.c
11
pb_encode.c
@@ -48,7 +48,11 @@ static bool checkreturn buf_write(pb_ostream_t *stream, const uint8_t *buf, size
|
|||||||
pb_ostream_t pb_ostream_from_buffer(uint8_t *buf, size_t bufsize)
|
pb_ostream_t pb_ostream_from_buffer(uint8_t *buf, size_t bufsize)
|
||||||
{
|
{
|
||||||
pb_ostream_t stream;
|
pb_ostream_t stream;
|
||||||
|
#ifdef PB_BUFFER_ONLY
|
||||||
|
stream.callback = (void*)1; /* Just some marker value */
|
||||||
|
#else
|
||||||
stream.callback = &buf_write;
|
stream.callback = &buf_write;
|
||||||
|
#endif
|
||||||
stream.state = buf;
|
stream.state = buf;
|
||||||
stream.max_size = bufsize;
|
stream.max_size = bufsize;
|
||||||
stream.bytes_written = 0;
|
stream.bytes_written = 0;
|
||||||
@@ -61,9 +65,14 @@ bool checkreturn pb_write(pb_ostream_t *stream, const uint8_t *buf, size_t count
|
|||||||
{
|
{
|
||||||
if (stream->bytes_written + count > stream->max_size)
|
if (stream->bytes_written + count > stream->max_size)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
|
#ifdef PB_BUFFER_ONLY
|
||||||
|
if (!buf_write(stream, buf, count))
|
||||||
|
return false;
|
||||||
|
#else
|
||||||
if (!stream->callback(stream, buf, count))
|
if (!stream->callback(stream, buf, count))
|
||||||
return false;
|
return false;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
stream->bytes_written += count;
|
stream->bytes_written += count;
|
||||||
|
|||||||
10
pb_encode.h
10
pb_encode.h
@@ -32,7 +32,17 @@ extern "C" {
|
|||||||
*/
|
*/
|
||||||
struct _pb_ostream_t
|
struct _pb_ostream_t
|
||||||
{
|
{
|
||||||
|
#ifdef PB_BUFFER_ONLY
|
||||||
|
/* Callback pointer is not used in buffer-only configuration.
|
||||||
|
* Having an int pointer here allows binary compatibility but
|
||||||
|
* gives an error if someone tries to assign callback function.
|
||||||
|
* Also, NULL pointer marks a 'sizing stream' that does not
|
||||||
|
* write anything.
|
||||||
|
*/
|
||||||
|
int *callback;
|
||||||
|
#else
|
||||||
bool (*callback)(pb_ostream_t *stream, const uint8_t *buf, size_t count);
|
bool (*callback)(pb_ostream_t *stream, const uint8_t *buf, size_t count);
|
||||||
|
#endif
|
||||||
void *state; /* Free field for use by callback implementation */
|
void *state; /* Free field for use by callback implementation */
|
||||||
size_t max_size; /* Limit number of output bytes written (or use SIZE_MAX). */
|
size_t max_size; /* Limit number of output bytes written (or use SIZE_MAX). */
|
||||||
size_t bytes_written;
|
size_t bytes_written;
|
||||||
|
|||||||
@@ -3,8 +3,8 @@ DEPS=../pb_decode.h ../pb_encode.h ../pb.h person.pb.h \
|
|||||||
callbacks2.pb.h callbacks.pb.h unittests.h unittestproto.pb.h \
|
callbacks2.pb.h callbacks.pb.h unittests.h unittestproto.pb.h \
|
||||||
alltypes.pb.h missing_fields.pb.h
|
alltypes.pb.h missing_fields.pb.h
|
||||||
TESTS= decode_unittests encode_unittests \
|
TESTS= decode_unittests encode_unittests \
|
||||||
test_decode1 test_decode2 test_decode3 \
|
test_decode1 test_decode2 test_decode3 test_decode3_buf \
|
||||||
test_encode1 test_encode2 test_encode3 \
|
test_encode1 test_encode2 test_encode3 test_encode3_buf \
|
||||||
test_decode_callbacks test_encode_callbacks \
|
test_decode_callbacks test_encode_callbacks \
|
||||||
test_missing_fields test_no_messages \
|
test_missing_fields test_no_messages \
|
||||||
test_multiple_files test_cxxcompile test_options \
|
test_multiple_files test_cxxcompile test_options \
|
||||||
@@ -39,11 +39,26 @@ pb_encode.o: ../pb_encode.c $(DEPS)
|
|||||||
pb_decode.o: ../pb_decode.c $(DEPS)
|
pb_decode.o: ../pb_decode.c $(DEPS)
|
||||||
$(CC) $(CFLAGS) $(CFLAGS_CORE) -c -o $@ $<
|
$(CC) $(CFLAGS) $(CFLAGS_CORE) -c -o $@ $<
|
||||||
|
|
||||||
|
# Test for compilability with c++ compiler
|
||||||
|
|
||||||
pb_encode.cxx.o: ../pb_encode.c $(DEPS)
|
pb_encode.cxx.o: ../pb_encode.c $(DEPS)
|
||||||
$(CXX) $(CFLAGS) $(CFLAGS_CORE) -c -o $@ $<
|
$(CXX) $(CFLAGS) $(CFLAGS_CORE) -c -o $@ $<
|
||||||
pb_decode.cxx.o: ../pb_decode.c $(DEPS)
|
pb_decode.cxx.o: ../pb_decode.c $(DEPS)
|
||||||
$(CXX) $(CFLAGS) $(CFLAGS_CORE) -c -o $@ $<
|
$(CXX) $(CFLAGS) $(CFLAGS_CORE) -c -o $@ $<
|
||||||
|
|
||||||
|
# Test for PB_BUF_ONLY compilation option
|
||||||
|
|
||||||
|
pb_encode.buf.o: ../pb_encode.c $(DEPS)
|
||||||
|
$(CC) -DPB_BUFFER_ONLY $(CFLAGS) $(CFLAGS_CORE) -c -o $@ $<
|
||||||
|
pb_decode.buf.o: ../pb_decode.c $(DEPS)
|
||||||
|
$(CC) -DPB_BUFFER_ONLY $(CFLAGS) $(CFLAGS_CORE) -c -o $@ $<
|
||||||
|
%.buf.o: %.c $(DEPS)
|
||||||
|
$(CC) -DPB_BUFFER_ONLY $(CFLAGS) -c -o $@ $<
|
||||||
|
test_encode3_buf: test_encode3.buf.o pb_encode.buf.o alltypes.pb.o
|
||||||
|
$(CC) $(LDFLAGS) $^ -o $@
|
||||||
|
test_decode3_buf: test_decode3.buf.o pb_decode.buf.o alltypes.pb.o
|
||||||
|
$(CC) $(LDFLAGS) $^ -o $@
|
||||||
|
|
||||||
test_cxxcompile: pb_encode.cxx.o pb_decode.cxx.o
|
test_cxxcompile: pb_encode.cxx.o pb_decode.cxx.o
|
||||||
test_decode1: test_decode1.o pb_decode.o person.pb.o
|
test_decode1: test_decode1.o pb_decode.o person.pb.o
|
||||||
test_decode2: test_decode2.o pb_decode.o person.pb.o
|
test_decode2: test_decode2.o pb_decode.o person.pb.o
|
||||||
@@ -98,6 +113,7 @@ run_unittests: $(TESTS)
|
|||||||
./test_encode3 | ./test_decode3
|
./test_encode3 | ./test_decode3
|
||||||
./test_encode3 1 | ./test_decode3 1
|
./test_encode3 1 | ./test_decode3 1
|
||||||
./test_encode3 1 | protoc --decode=AllTypes -I. -I../generator -I/usr/include alltypes.proto >/dev/null
|
./test_encode3 1 | protoc --decode=AllTypes -I. -I../generator -I/usr/include alltypes.proto >/dev/null
|
||||||
|
./test_encode3_buf 1 | ./test_decode3_buf 1
|
||||||
./bc_encode | ./bc_decode
|
./bc_encode | ./bc_decode
|
||||||
|
|
||||||
./test_missing_fields
|
./test_missing_fields
|
||||||
|
|||||||
Reference in New Issue
Block a user