Skip to content

Commit 9627348

Browse files
Chunk getSerializedSize() into 32 field chunks to make it more JIT friendly.
This follows the precedent that was previously done for buildPartial (including the exact number of fields per chunk). PiperOrigin-RevId: 866458607
1 parent 9b00a7b commit 9627348

File tree

1 file changed

+30
-4
lines changed

1 file changed

+30
-4
lines changed

src/google/protobuf/compiler/java/full/message.cc

Lines changed: 30 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111

1212
#include "google/protobuf/compiler/java/full/message.h"
1313

14+
#include <algorithm>
1415
#include <memory>
1516
#include <string>
1617
#include <utility>
@@ -608,9 +609,33 @@ void ImmutableMessageGenerator::GenerateMessageSerializationMethods(
608609
}
609610

610611
printer->Outdent();
612+
printer->Print("}\n");
613+
614+
// Chunk up the getSerializedSize() into chunks to be JIT friendly.
615+
constexpr int kNumFieldsPerChunk = 32;
616+
int num_chunks = (descriptor_->field_count() + kNumFieldsPerChunk - 1) /
617+
kNumFieldsPerChunk;
618+
for (int i = 0; i < num_chunks; ++i) {
619+
printer->Print(
620+
"private int computeSerializedSize_$chunk$() {\n"
621+
" int size = 0;\n",
622+
"chunk", absl::StrCat(i));
623+
printer->Indent();
624+
625+
int chunk_field_start = i * kNumFieldsPerChunk;
626+
int chunk_field_end = std::min(chunk_field_start + kNumFieldsPerChunk,
627+
descriptor_->field_count());
628+
629+
for (int j = chunk_field_start; j < chunk_field_end; ++j) {
630+
field_generators_.get(sorted_fields[j])
631+
.GenerateSerializedSizeCode(printer);
632+
}
633+
printer->Outdent();
634+
printer->Print(" return size;\n");
635+
printer->Print("}\n");
636+
}
637+
611638
printer->Print(
612-
"}\n"
613-
"\n"
614639
"@java.lang.Override\n"
615640
"public int getSerializedSize() {\n"
616641
" int size = memoizedSize;\n"
@@ -620,8 +645,9 @@ void ImmutableMessageGenerator::GenerateMessageSerializationMethods(
620645

621646
printer->Print("size = 0;\n");
622647

623-
for (int i = 0; i < descriptor_->field_count(); i++) {
624-
field_generators_.get(sorted_fields[i]).GenerateSerializedSizeCode(printer);
648+
for (int i = 0; i < num_chunks; ++i) {
649+
printer->Print("size += computeSerializedSize_$chunk$();\n", "chunk",
650+
absl::StrCat(i));
625651
}
626652

627653
if (descriptor_->extension_range_count() > 0) {

0 commit comments

Comments
 (0)