From 9951233e9a5c23ad285b0286e7e896bfd46f8397 Mon Sep 17 00:00:00 2001 From: "jasonh+personal@google.com" Date: Tue, 1 Dec 2009 18:05:21 +0000 Subject: Fix Issue 136: the memoized serialized size for packed fields may not be properly set. writeTo() may be invoked without a call to getSerializedSize(), so the generated serialization methods would write a length of 0 for non-empty packed fields. Just call getSerializedSize() at the beginning of writeTo(): although this means that we may compute the byte size needlessly when there are no packed fields, in practice, getSerializedSize() will already have been called - all of the writeTo() wrappers in AbstractMessageLite invoke it. Tested: new unittest case in WireFormatTest.java now passes --- .../java/com/google/protobuf/WireFormatTest.java | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) (limited to 'java/src') diff --git a/java/src/test/java/com/google/protobuf/WireFormatTest.java b/java/src/test/java/com/google/protobuf/WireFormatTest.java index bd1c6db1..6a5bd5de 100644 --- a/java/src/test/java/com/google/protobuf/WireFormatTest.java +++ b/java/src/test/java/com/google/protobuf/WireFormatTest.java @@ -102,6 +102,28 @@ public class WireFormatTest extends TestCase { assertEquals(rawBytes, rawBytes2); } + public void testSerializationPackedWithoutGetSerializedSize() + throws Exception { + // Write directly to an OutputStream, without invoking getSerializedSize() + // This used to be a bug where the size of a packed field was incorrect, + // since getSerializedSize() was never invoked. + TestPackedTypes message = TestUtil.getPackedSet(); + + // Directly construct a CodedOutputStream around the actual OutputStream, + // in case writeTo(OutputStream output) invokes getSerializedSize(); + ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); + CodedOutputStream codedOutput = CodedOutputStream.newInstance(outputStream); + + message.writeTo(codedOutput); + + codedOutput.flush(); + + TestPackedTypes message2 = TestPackedTypes.parseFrom( + outputStream.toByteArray()); + + TestUtil.assertPackedFieldsSet(message2); + } + public void testSerializeExtensionsLite() throws Exception { // TestAllTypes and TestAllExtensions should have compatible wire formats, // so if we serialize a TestAllExtensions then parse it as TestAllTypes -- cgit v1.2.3