Skip to content

Commit

Permalink
Fix problem with [default=xxxx, (nanopb).proto3=true] field option co…
Browse files Browse the repository at this point in the history
…mbination (#558)
  • Loading branch information
PetteriAimonen committed Sep 10, 2020
1 parent d1be4fe commit 4b455da
Show file tree
Hide file tree
Showing 4 changed files with 74 additions and 0 deletions.
9 changes: 9 additions & 0 deletions pb_encode.c
Expand Up @@ -265,6 +265,15 @@ static bool checkreturn pb_check_proto3_default_value(const pb_field_iter_t *fie
* submessage fields. */
return safe_read_bool(field->pSize) == false;
}
else if (field->descriptor->default_value)
{
/* Proto3 messages do not have default values, but proto2 messages
* can contain optional fields without has_fields (generator option 'proto3').
* In this case they must always be encoded, to make sure that the
* non-zero default value is overwritten.
*/
return false;
}

/* Rest is proto3 singular fields */
if (PB_LTYPE(type) <= PB_LTYPE_LAST_PACKABLE)
Expand Down
8 changes: 8 additions & 0 deletions tests/regression/issue_558/SConscript
@@ -0,0 +1,8 @@
# Regression test for #558:
# Manually defining proto3:true on a field with default value incorrectly omits it when encoding.

Import("env")
env.NanopbProto("mixed")

test = env.Program(["mixed.c", "mixed.pb.c", "$COMMON/pb_encode.o", "$COMMON/pb_decode.o", "$COMMON/pb_common.o"])
env.RunTest(test)
49 changes: 49 additions & 0 deletions tests/regression/issue_558/mixed.c
@@ -0,0 +1,49 @@
#include <pb_encode.h>
#include <pb_decode.h>

#include "mixed.pb.h"
#include "unittests.h"

int main()
{
int status = 0;
pb_byte_t buf[64];
size_t msglen;

{
pb_ostream_t ostream = pb_ostream_from_buffer(buf, sizeof(buf));
MixedMessage msg = MixedMessage_init_default;

msg.has_proto2_value = true;
msg.proto2_value = 0;
msg.proto3_value = 0;

if (!pb_encode(&ostream, MixedMessage_fields, &msg))
{
fprintf(stderr, "pb_encode() failed: %s\n", PB_GET_ERROR(&ostream));
return 1;
}

msglen = ostream.bytes_written;
TEST(msglen > 0);
}

{
pb_istream_t istream = pb_istream_from_buffer(buf, msglen);
MixedMessage msg = MixedMessage_init_default;

TEST(msg.proto2_value == 100);
TEST(msg.proto3_value == 200);

if (!pb_decode(&istream, MixedMessage_fields, &msg))
{
fprintf(stderr, "pb_decode() failed: %s\n", PB_GET_ERROR(&istream));
return 1;
}

TEST(msg.proto2_value == 0);
TEST(msg.proto3_value == 0);
}

return status;
}
8 changes: 8 additions & 0 deletions tests/regression/issue_558/mixed.proto
@@ -0,0 +1,8 @@
syntax = "proto2";

import "nanopb.proto";

message MixedMessage {
optional int32 proto2_value = 1 [default = 100];
optional int32 proto3_value = 2 [default = 200, (nanopb).proto3 = true];
}

0 comments on commit 4b455da

Please sign in to comment.