Skip to content

Commit eb68484

Browse files
Do Not Submit
PiperOrigin-RevId: 810510110
1 parent 265909f commit eb68484

File tree

8 files changed

+216
-67
lines changed

8 files changed

+216
-67
lines changed

src/google/protobuf/compiler/cpp/message.cc

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5296,7 +5296,7 @@ void MessageGenerator::GenerateByteSize(io::Printer* p) {
52965296
$WeakDescriptorSelfPin$;
52975297
$annotate_bytesize$;
52985298
// @@protoc_insertion_point(message_set_byte_size_start:$full_name$)
5299-
::size_t total_size = this_.$extensions$.MessageSetByteSize();
5299+
::size_t total_size = this_.$extensions$.MessageSetByteSize(&this_);
53005300
if (this_.$have_unknown_fields$) {
53015301
total_size += ::_pbi::ComputeUnknownMessageSetItemsSize(
53025302
this_.$unknown_fields$);
@@ -5354,7 +5354,7 @@ void MessageGenerator::GenerateByteSize(io::Printer* p) {
53545354
[&] {
53555355
if (descriptor_->extension_range_count() == 0) return;
53565356
p->Emit(R"cc(
5357-
total_size += this_.$extensions$.ByteSize();
5357+
total_size += this_.$extensions$.ByteSize(&this_);
53585358
)cc");
53595359
}},
53605360
{"prefetch",

src/google/protobuf/descriptor.pb.cc

Lines changed: 12 additions & 12 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/google/protobuf/extension_set.cc

Lines changed: 70 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@
1717
#include <cstddef>
1818
#include <cstdint>
1919
#include <string>
20-
#include <tuple>
2120
#include <type_traits>
2221
#include <utility>
2322
#include <variant>
@@ -375,11 +374,18 @@ void* ExtensionSet::MutableRawRepeatedField(int number) {
375374
// -------------------------------------------------------------------
376375
// Enums
377376

378-
size_t ExtensionSet::GetMessageByteSizeLong(int number) const {
377+
size_t ExtensionSet::GetMessageByteSizeLong(const MessageLite* extendee,
378+
int number) const {
379379
const Extension* extension = FindOrNull(number);
380380
ABSL_CHECK(extension != nullptr) << "not present";
381381
ABSL_DCHECK_TYPE(*extension, OPTIONAL_FIELD, MESSAGE);
382-
return extension->is_lazy ? extension->ptr.lazymessage_value->ByteSizeLong()
382+
ABSL_DCHECK(!extension->is_lazy ||
383+
GetOrFindPrototypeForLazyMessage(*extension, extendee, number) !=
384+
nullptr);
385+
return extension->is_lazy ? extension->ptr.lazymessage_value->ByteSizeLong(
386+
GetOrFindPrototypeForLazyMessage(
387+
*extension, extendee, number),
388+
extendee->GetArena())
383389
: extension->ptr.message_value->ByteSizeLong();
384390
}
385391

@@ -946,8 +952,8 @@ void ExtensionSet::InternalExtensionMergeFrom(Arena* arena,
946952
Arena* other_arena) {
947953
DebugAssertArenaMatches(arena);
948954
Extension* dst_extension;
949-
bool is_new = MaybeNewExtension(arena, number, other_extension.descriptor,
950-
&dst_extension);
955+
bool is_new = MaybeNewExtension(
956+
arena, number, other_extension.descriptor_or_prototype, &dst_extension);
951957
if (is_new) {
952958
InternalExtensionMergeFromIntoUninitializedExtension(
953959
arena, *dst_extension, extendee, number, other_extension, other_arena);
@@ -1009,9 +1015,12 @@ void ExtensionSet::InternalExtensionMergeFrom(Arena* arena,
10091015
ABSL_DCHECK(!dst_extension->is_repeated);
10101016
if (other_extension.is_lazy) {
10111017
if (dst_extension->is_lazy) {
1018+
const MessageLite* prototype = GetOrFindPrototypeForLazyMessage(
1019+
other_extension, extendee, number);
1020+
ABSL_DCHECK_NE(prototype, nullptr);
10121021
dst_extension->ptr.lazymessage_value->MergeFrom(
1013-
GetPrototypeForLazyMessage(extendee, number),
1014-
*other_extension.ptr.lazymessage_value, arena, other_arena);
1022+
prototype, *other_extension.ptr.lazymessage_value, arena,
1023+
other_arena);
10151024
} else {
10161025
dst_extension->ptr.message_value->CheckTypeAndMergeFrom(
10171026
other_extension.ptr.lazymessage_value->GetMessage(
@@ -1236,11 +1245,11 @@ uint8_t* ExtensionSet::InternalSerializeMessageSetWithCachedSizesToArray(
12361245
return target;
12371246
}
12381247

1239-
size_t ExtensionSet::ByteSize() const {
1248+
size_t ExtensionSet::ByteSize(const MessageLite* extendee) const {
12401249
size_t total_size = 0;
12411250
ForEach(
1242-
[&total_size](int number, const Extension& ext) {
1243-
total_size += ext.ByteSize(number);
1251+
[&](int number, const Extension& ext) {
1252+
total_size += ext.ByteSize(extendee, number, extendee->GetArena());
12441253
},
12451254
Prefetch{});
12461255
return total_size;
@@ -1250,12 +1259,15 @@ size_t ExtensionSet::ByteSize() const {
12501259
// Defined in extension_set_heavy.cc.
12511260
// int ExtensionSet::SpaceUsedExcludingSelf() const
12521261

1253-
bool ExtensionSet::MaybeNewExtension(Arena* arena, int number,
1254-
const FieldDescriptor* descriptor,
1255-
Extension** result) {
1256-
bool extension_is_new = false;
1257-
std::tie(*result, extension_is_new) = Insert(arena, number);
1258-
(*result)->descriptor = descriptor;
1262+
bool ExtensionSet::MaybeNewExtension(
1263+
Arena* arena, int number,
1264+
Extension::DescriptorOrPrototype descriptor_or_prototype,
1265+
Extension** result_ptr) {
1266+
auto [result, extension_is_new] = Insert(arena, number);
1267+
*result_ptr = result;
1268+
if (extension_is_new) {
1269+
result->descriptor_or_prototype = descriptor_or_prototype;
1270+
}
12591271
return extension_is_new;
12601272
}
12611273

@@ -1327,7 +1339,8 @@ void ExtensionSet::Extension::Clear() {
13271339
}
13281340
}
13291341

1330-
size_t ExtensionSet::Extension::ByteSize(int number) const {
1342+
size_t ExtensionSet::Extension::ByteSize(const MessageLite* extendee,
1343+
int number, Arena* arena) const {
13311344
size_t result = 0;
13321345

13331346
if (is_repeated) {
@@ -1443,7 +1456,10 @@ size_t ExtensionSet::Extension::ByteSize(int number) const {
14431456
#undef HANDLE_TYPE
14441457
case WireFormatLite::TYPE_MESSAGE: {
14451458
result += WireFormatLite::LengthDelimitedSize(
1446-
is_lazy ? ptr.lazymessage_value->ByteSizeLong()
1459+
is_lazy ? ptr.lazymessage_value->ByteSizeLong(
1460+
ExtensionSet::GetOrFindPrototypeForLazyMessage(
1461+
*this, extendee, number),
1462+
arena)
14471463
: ptr.message_value->ByteSizeLong());
14481464
break;
14491465
}
@@ -1554,7 +1570,7 @@ bool ExtensionSet::Extension::IsInitialized(const ExtensionSet* ext_set,
15541570
if (!is_lazy) return ptr.message_value->IsInitialized();
15551571

15561572
const MessageLite* prototype =
1557-
ext_set->GetPrototypeForLazyMessage(extendee, number);
1573+
ext_set->GetOrFindPrototypeForLazyMessage(*this, extendee, number);
15581574
ABSL_DCHECK_NE(prototype, nullptr)
15591575
<< "extendee: " << extendee->GetTypeName() << "; number: " << number;
15601576
return ptr.lazymessage_value->IsInitialized(prototype, arena);
@@ -1857,7 +1873,9 @@ uint8_t* ExtensionSet::Extension::InternalSerializeFieldWithCachedSizesToArray(
18571873
case WireFormatLite::TYPE_MESSAGE:
18581874
if (is_lazy) {
18591875
const auto* prototype =
1860-
extension_set->GetPrototypeForLazyMessage(extendee, number);
1876+
extension_set->GetOrFindPrototypeForLazyMessage(*this, extendee,
1877+
number);
1878+
ABSL_DCHECK_NE(prototype, nullptr);
18611879
target = ptr.lazymessage_value->WriteMessageToArray(prototype, number,
18621880
target, stream);
18631881
} else {
@@ -1871,7 +1889,8 @@ uint8_t* ExtensionSet::Extension::InternalSerializeFieldWithCachedSizesToArray(
18711889
return target;
18721890
}
18731891

1874-
const MessageLite* ExtensionSet::GetPrototypeForLazyMessage(
1892+
template <bool mustBeGenerated>
1893+
const MessageLite* ExtensionSet::FindPrototypeForLazyMessageImpl(
18751894
const MessageLite* extendee, int number) {
18761895
GeneratedExtensionFinder finder(extendee);
18771896
bool was_packed_on_wire = false;
@@ -1881,9 +1900,25 @@ const MessageLite* ExtensionSet::GetPrototypeForLazyMessage(
18811900
&extension_info, &was_packed_on_wire)) {
18821901
return nullptr;
18831902
}
1903+
if constexpr (mustBeGenerated) {
1904+
if (!extension_info.IsGenerated()) return nullptr;
1905+
}
18841906
return extension_info.message_info.prototype;
18851907
}
18861908

1909+
const MessageLite* ExtensionSet::FindPrototypeForLazyMessage(
1910+
const MessageLite* extendee, int number) {
1911+
return FindPrototypeForLazyMessageImpl</*mustBeGenerated=*/false>(extendee,
1912+
number);
1913+
}
1914+
1915+
const MessageLite*
1916+
ExtensionSet::FindPrototypeFromGeneratedFactoryForLazyMessage(
1917+
const MessageLite* extendee, int number) {
1918+
return FindPrototypeForLazyMessageImpl</*mustBeGenerated=*/true>(extendee,
1919+
number);
1920+
}
1921+
18871922
uint8_t*
18881923
ExtensionSet::Extension::InternalSerializeMessageSetItemWithCachedSizesToArray(
18891924
const MessageLite* extendee, const ExtensionSet* extension_set, int number,
@@ -1906,8 +1941,9 @@ ExtensionSet::Extension::InternalSerializeMessageSetItemWithCachedSizesToArray(
19061941
WireFormatLite::kMessageSetTypeIdNumber, number, target);
19071942
// Write message.
19081943
if (is_lazy) {
1909-
const auto* prototype =
1910-
extension_set->GetPrototypeForLazyMessage(extendee, number);
1944+
const auto* prototype = extension_set->GetOrFindPrototypeForLazyMessage(
1945+
*this, extendee, number);
1946+
ABSL_DCHECK_NE(prototype, nullptr);
19111947
target = ptr.lazymessage_value->WriteMessageToArray(
19121948
prototype, WireFormatLite::kMessageSetMessageNumber, target, stream);
19131949
} else {
@@ -1922,11 +1958,12 @@ ExtensionSet::Extension::InternalSerializeMessageSetItemWithCachedSizesToArray(
19221958
return target;
19231959
}
19241960

1925-
size_t ExtensionSet::Extension::MessageSetItemByteSize(int number) const {
1961+
size_t ExtensionSet::Extension::MessageSetItemByteSize(
1962+
const MessageLite* extendee, int number, Arena* arena) const {
19261963
if (type != WireFormatLite::TYPE_MESSAGE || is_repeated) {
19271964
// Not a valid MessageSet extension, but compute the byte size for it the
19281965
// normal way.
1929-
return ByteSize(number);
1966+
return ByteSize(extendee, number, arena);
19301967
}
19311968

19321969
if (is_cleared) return 0;
@@ -1938,17 +1975,21 @@ size_t ExtensionSet::Extension::MessageSetItemByteSize(int number) const {
19381975

19391976
// message
19401977
our_size += WireFormatLite::LengthDelimitedSize(
1941-
is_lazy ? ptr.lazymessage_value->ByteSizeLong()
1978+
is_lazy ? ptr.lazymessage_value->ByteSizeLong(
1979+
ExtensionSet::GetOrFindPrototypeForLazyMessage(
1980+
*this, extendee, number),
1981+
arena)
19421982
: ptr.message_value->ByteSizeLong());
19431983

19441984
return our_size;
19451985
}
19461986

1947-
size_t ExtensionSet::MessageSetByteSize() const {
1987+
size_t ExtensionSet::MessageSetByteSize(const MessageLite* extendee) const {
19481988
size_t total_size = 0;
19491989
ForEach(
1950-
[&total_size](int number, const Extension& ext) {
1951-
total_size += ext.MessageSetItemByteSize(number);
1990+
[&](int number, const Extension& ext) {
1991+
total_size +=
1992+
ext.MessageSetItemByteSize(extendee, number, extendee->GetArena());
19521993
},
19531994
Prefetch{});
19541995
return total_size;

0 commit comments

Comments
 (0)