Skip to content

Commit b68b673

Browse files
Improve Java gencode static initialization to avoid unnecessary temporaries
PiperOrigin-RevId: 799633296
1 parent 25d8081 commit b68b673

File tree

6 files changed

+167
-25
lines changed

6 files changed

+167
-25
lines changed

‎java/core/src/main/java/com/google/protobuf/Descriptors.java‎

Lines changed: 105 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -211,21 +211,53 @@ public List<Descriptor> getMessageTypes() {
211211
return Collections.unmodifiableList(Arrays.asList(messageTypes));
212212
}
213213

214+
public int getMessageTypeCount() {
215+
return messageTypes.length;
216+
}
217+
218+
public Descriptor getMessageType(int index) {
219+
return messageTypes[index];
220+
}
221+
214222
/** Get a list of top-level enum types declared in this file. */
215223
public List<EnumDescriptor> getEnumTypes() {
216224
return Collections.unmodifiableList(Arrays.asList(enumTypes));
217225
}
218226

227+
public int getEnumTypeCount() {
228+
return enumTypes.length;
229+
}
230+
231+
public EnumDescriptor getEnumType(int index) {
232+
return enumTypes[index];
233+
}
234+
219235
/** Get a list of top-level services declared in this file. */
220236
public List<ServiceDescriptor> getServices() {
221237
return Collections.unmodifiableList(Arrays.asList(services));
222238
}
223239

240+
public int getServiceCount() {
241+
return services.length;
242+
}
243+
244+
public ServiceDescriptor getService(int index) {
245+
return services[index];
246+
}
247+
224248
/** Get a list of top-level extensions declared in this file. */
225249
public List<FieldDescriptor> getExtensions() {
226250
return Collections.unmodifiableList(Arrays.asList(extensions));
227251
}
228252

253+
public int getExtensionCount() {
254+
return extensions.length;
255+
}
256+
257+
public FieldDescriptor getExtension(int index) {
258+
return extensions[index];
259+
}
260+
229261
/** Get a list of this file's dependencies (imports). */
230262
public List<FileDescriptor> getDependencies() {
231263
return Collections.unmodifiableList(Arrays.asList(dependencies));
@@ -844,31 +876,94 @@ public List<FieldDescriptor> getFields() {
844876
return Collections.unmodifiableList(Arrays.asList(fields));
845877
}
846878

879+
/** Get a count of this message type's fields. */
880+
public int getFieldCount() {
881+
return fields.length;
882+
}
883+
884+
/** Get the message type's field at the specified index. */
885+
public FieldDescriptor getField(int index) {
886+
return fields[index];
887+
}
888+
847889
/** Get a list of this message type's oneofs. */
848890
public List<OneofDescriptor> getOneofs() {
849891
return Collections.unmodifiableList(Arrays.asList(oneofs));
850892
}
851893

894+
/** Get a count of this message type's oneofs. */
895+
public int getOneofCount() {
896+
return oneofs.length;
897+
}
898+
899+
/** Get the message type's oneof at the specified index. */
900+
public OneofDescriptor getOneof(int index) {
901+
return oneofs[index];
902+
}
903+
852904
/** Get a list of this message type's real oneofs. */
853905
public List<OneofDescriptor> getRealOneofs() {
854906
return Collections.unmodifiableList(Arrays.asList(oneofs).subList(0, realOneofCount));
855907
}
856908

909+
/** Get a count of this message type's real oneofs. */
910+
public int getRealOneofCount() {
911+
return realOneofCount;
912+
}
913+
914+
/** Get the message type's real oneof at the specified index. */
915+
public OneofDescriptor getRealOneof(int index) {
916+
if (index >= realOneofCount) {
917+
throw new ArrayIndexOutOfBoundsException(index);
918+
}
919+
return oneofs[index];
920+
}
921+
857922
/** Get a list of the extensions defined nested within this message type's scope. */
858923
public List<FieldDescriptor> getExtensions() {
859924
return Collections.unmodifiableList(Arrays.asList(extensions));
860925
}
861926

927+
/** Get a count of the extensions defined nested within this message type's scope. */
928+
public int getExtensionCount() {
929+
return extensions.length;
930+
}
931+
932+
/** Get the extension defined nested within this message type's scope at the specified index. */
933+
public FieldDescriptor getExtension(int index) {
934+
return extensions[index];
935+
}
936+
862937
/** Get a list of message types nested within this one. */
863938
public List<Descriptor> getNestedTypes() {
864939
return Collections.unmodifiableList(Arrays.asList(nestedTypes));
865940
}
866941

942+
/** Get a count of message types nested within this one. */
943+
public int getNestedTypeCount() {
944+
return nestedTypes.length;
945+
}
946+
947+
/** Get the message type's nested message type at the specified index. */
948+
public Descriptor getNestedType(int index) {
949+
return nestedTypes[index];
950+
}
951+
867952
/** Get a list of enum types nested within this one. */
868953
public List<EnumDescriptor> getEnumTypes() {
869954
return Collections.unmodifiableList(Arrays.asList(enumTypes));
870955
}
871956

957+
/** Get a count of enum types nested within this one. */
958+
public int getEnumTypeCount() {
959+
return enumTypes.length;
960+
}
961+
962+
/** Get the message type's nested enum type at the specified index. */
963+
public EnumDescriptor getEnumType(int index) {
964+
return enumTypes[index];
965+
}
966+
872967
/** Determines if the given field number is an extension. */
873968
public boolean isExtensionNumber(final int number) {
874969
int index = Arrays.binarySearch(extensionRangeLowerBounds, number);
@@ -2633,6 +2728,16 @@ public List<MethodDescriptor> getMethods() {
26332728
return Collections.unmodifiableList(Arrays.asList(methods));
26342729
}
26352730

2731+
/** Get a count of methods for this service. */
2732+
public int getMethodCount() {
2733+
return methods.length;
2734+
}
2735+
2736+
/** Get the service's method at the specified index. */
2737+
public MethodDescriptor getMethod(int index) {
2738+
return methods[index];
2739+
}
2740+
26362741
/**
26372742
* Find a method by name.
26382743
*

‎java/core/src/main/java/com/google/protobuf/GeneratedMessage.java‎

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1797,7 +1797,7 @@ GeneratedExtension<ContainingT, T> newMessageScopedGeneratedExtension(
17971797
new CachedDescriptorRetriever() {
17981798
@Override
17991799
public FieldDescriptor loadDescriptor() {
1800-
return scope.getDescriptorForType().getExtensions().get(descriptorIndex);
1800+
return scope.getDescriptorForType().getExtension(descriptorIndex);
18011801
}
18021802
},
18031803
singularType,
@@ -2151,8 +2151,8 @@ public FieldAccessorTable(
21512151
public FieldAccessorTable(final Descriptor descriptor, final String[] camelCaseNames) {
21522152
this.descriptor = descriptor;
21532153
this.camelCaseNames = camelCaseNames;
2154-
fields = new FieldAccessor[descriptor.getFields().size()];
2155-
oneofs = new OneofAccessor[descriptor.getOneofs().size()];
2154+
fields = new FieldAccessor[descriptor.getFieldCount()];
2155+
oneofs = new OneofAccessor[descriptor.getOneofCount()];
21562156
initialized = false;
21572157
}
21582158

@@ -2175,7 +2175,7 @@ public FieldAccessorTable ensureFieldAccessorsInitialized(
21752175
}
21762176
int fieldsSize = fields.length;
21772177
for (int i = 0; i < fieldsSize; i++) {
2178-
FieldDescriptor field = descriptor.getFields().get(i);
2178+
FieldDescriptor field = descriptor.getField(i);
21792179
String containingOneofCamelCaseName = null;
21802180
if (field.getContainingOneof() != null) {
21812181
int index = fieldsSize + field.getContainingOneof().getIndex();
@@ -2235,8 +2235,8 @@ public FieldAccessorTable ensureFieldAccessorsInitialized(
22352235
}
22362236
}
22372237

2238-
for (int i = 0; i < descriptor.getOneofs().size(); i++) {
2239-
if (i < descriptor.getRealOneofs().size()) {
2238+
for (int i = 0; i < descriptor.getOneofCount(); i++) {
2239+
if (i < descriptor.getRealOneofCount()) {
22402240
oneofs[i] =
22412241
new RealOneofAccessor(
22422242
descriptor, camelCaseNames[i + fieldsSize], messageClass, builderClass);
@@ -2383,8 +2383,8 @@ public void clear(final Builder<?> builder) {
23832383
/** SyntheticOneofAccessor provides access to a single synthetic oneof. */
23842384
private static class SyntheticOneofAccessor implements OneofAccessor {
23852385
SyntheticOneofAccessor(final Descriptor descriptor, final int oneofIndex) {
2386-
OneofDescriptor oneofDescriptor = descriptor.getOneofs().get(oneofIndex);
2387-
fieldDescriptor = oneofDescriptor.getFields().get(0);
2386+
OneofDescriptor oneofDescriptor = descriptor.getOneof(oneofIndex);
2387+
fieldDescriptor = oneofDescriptor.getField(0);
23882388
}
23892389

23902390
private final FieldDescriptor fieldDescriptor;

‎java/core/src/main/java/com/google/protobuf/RuntimeVersion.java‎

Lines changed: 46 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77

88
package com.google.protobuf;
99

10+
import java.util.Locale;
1011
import java.util.logging.Logger;
1112

1213
/**
@@ -48,6 +49,28 @@ public enum RuntimeDomain {
4849
private static final String VERSION_STRING = versionString(MAJOR, MINOR, PATCH, SUFFIX);
4950
private static final Logger logger = Logger.getLogger(RuntimeVersion.class.getName());
5051

52+
/**
53+
* Validates that the gencode version is compatible with this runtime version according to
54+
* https://protobuf.dev/support/cross-version-runtime-guarantee/.
55+
*
56+
* <p>This method is currently only used by Protobuf Java **full version** gencode (<=32.x), it is
57+
* left for compatibility. Do not call it elsewhere.
58+
*
59+
* @param domain the domain where Protobuf Java code was generated.
60+
* @param major the major version of Protobuf Java gencode.
61+
* @param minor the minor version of Protobuf Java gencode.
62+
* @param patch the micro/patch version of Protobuf Java gencode.
63+
* @param suffix the version suffix e.g. "-rc2", "-dev", etc.
64+
* @param location the debugging location e.g. generated Java class to put in the error messages.
65+
* @deprecated Use other overload.
66+
* @throws ProtobufRuntimeVersionException if versions are incompatible.
67+
*/
68+
@Deprecated
69+
public static void validateProtobufGencodeVersion(
70+
RuntimeDomain domain, int major, int minor, int patch, String suffix, String location) {
71+
validateProtobufGencodeVersionImpl(domain, major, minor, patch, suffix, location);
72+
}
73+
5174
/**
5275
* Validates that the gencode version is compatible with this runtime version according to
5376
* https://protobuf.dev/support/cross-version-runtime-guarantee/.
@@ -64,13 +87,13 @@ public enum RuntimeDomain {
6487
* @throws ProtobufRuntimeVersionException if versions are incompatible.
6588
*/
6689
public static void validateProtobufGencodeVersion(
67-
RuntimeDomain domain, int major, int minor, int patch, String suffix, String location) {
90+
RuntimeDomain domain, int major, int minor, int patch, String suffix, Class<?> location) {
6891
validateProtobufGencodeVersionImpl(domain, major, minor, patch, suffix, location);
6992
}
7093

7194
/** The actual implementation of version validation. */
7295
private static void validateProtobufGencodeVersionImpl(
73-
RuntimeDomain domain, int major, int minor, int patch, String suffix, String location) {
96+
RuntimeDomain domain, int major, int minor, int patch, String suffix, Object location) {
7497
if (checkDisabled()) {
7598
return;
7699
}
@@ -84,9 +107,12 @@ private static void validateProtobufGencodeVersionImpl(
84107
if (domain != DOMAIN) {
85108
throw new ProtobufRuntimeVersionException(
86109
String.format(
110+
Locale.US,
87111
"Detected mismatched Protobuf Gencode/Runtime domains when loading %s: gencode %s,"
88112
+ " runtime %s. Cross-domain usage of Protobuf is not supported.",
89-
location, domain, DOMAIN));
113+
location,
114+
domain,
115+
DOMAIN));
90116
}
91117

92118
String gencodeVersionString = null;
@@ -97,17 +123,23 @@ private static void validateProtobufGencodeVersionImpl(
97123
gencodeVersionString = versionString(major, minor, patch, suffix);
98124
logger.warning(
99125
String.format(
126+
Locale.US,
100127
" Protobuf gencode version %s is exactly one major version older than the runtime"
101128
+ " version %s at %s. Please update the gencode to avoid compatibility"
102129
+ " violations in the next runtime release.",
103-
gencodeVersionString, VERSION_STRING, location));
130+
gencodeVersionString,
131+
VERSION_STRING,
132+
location));
104133
majorWarningLoggedCount++;
105134
} else {
106135
throw new ProtobufRuntimeVersionException(
107136
String.format(
137+
Locale.US,
108138
"Detected mismatched Protobuf Gencode/Runtime major versions when loading %s:"
109139
+ " gencode %s, runtime %s. Same major version is required.",
110-
location, versionString(major, minor, patch, suffix), VERSION_STRING));
140+
location,
141+
versionString(major, minor, patch, suffix),
142+
VERSION_STRING));
111143
}
112144
}
113145

@@ -118,9 +150,12 @@ private static void validateProtobufGencodeVersionImpl(
118150
}
119151
throw new ProtobufRuntimeVersionException(
120152
String.format(
153+
Locale.US,
121154
"Detected incompatible Protobuf Gencode/Runtime versions when loading %s: gencode %s,"
122155
+ " runtime %s. Runtime version cannot be older than the linked gencode version.",
123-
location, gencodeVersionString, VERSION_STRING));
156+
location,
157+
gencodeVersionString,
158+
VERSION_STRING));
124159
}
125160

126161
// Check that runtime version suffix is the same as the gencode version suffix.
@@ -130,9 +165,12 @@ private static void validateProtobufGencodeVersionImpl(
130165
}
131166
throw new ProtobufRuntimeVersionException(
132167
String.format(
168+
Locale.US,
133169
"Detected mismatched Protobuf Gencode/Runtime version suffixes when loading %s:"
134170
+ " gencode %s, runtime %s. Version suffixes must be the same.",
135-
location, gencodeVersionString, VERSION_STRING));
171+
location,
172+
gencodeVersionString,
173+
VERSION_STRING));
136174
}
137175
}
138176

@@ -148,7 +186,7 @@ public ProtobufRuntimeVersionException(String message) {
148186

149187
/** Gets the version string given the version segments. */
150188
private static String versionString(int major, int minor, int patch, String suffix) {
151-
return String.format("%d.%d.%d%s", major, minor, patch, suffix);
189+
return String.format(Locale.US, "%d.%d.%d%s", major, minor, patch, suffix);
152190
}
153191

154192
private static boolean checkDisabled() {

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

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -152,13 +152,12 @@ int ImmutableMessageGenerator::GenerateStaticVariableInitializers(
152152
if (descriptor_->containing_type() == nullptr) {
153153
printer->Print(vars,
154154
"internal_$identifier$_descriptor =\n"
155-
" getDescriptor().getMessageTypes().get($index$);\n");
155+
" getDescriptor().getMessageType($index$);\n");
156156
bytecode_estimate += 30;
157157
} else {
158-
printer->Print(
159-
vars,
160-
"internal_$identifier$_descriptor =\n"
161-
" internal_$parent$_descriptor.getNestedTypes().get($index$);\n");
158+
printer->Print(vars,
159+
"internal_$identifier$_descriptor =\n"
160+
" internal_$parent$_descriptor.getNestedType($index$);\n");
162161
bytecode_estimate += 30;
163162
}
164163

‎src/google/protobuf/compiler/java/full/service.cc‎

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,7 @@ void ImmutableServiceGenerator::Generate(io::Printer* printer) {
6565
"public static final\n"
6666
" com.google.protobuf.Descriptors.ServiceDescriptor\n"
6767
" getDescriptor() {\n"
68-
" return $file$.getDescriptor().getServices().get($index$);\n"
68+
" return $file$.getDescriptor().getService($index$);\n"
6969
"}\n",
7070
"file", name_resolver_->GetImmutableClassName(descriptor_->file()),
7171
"index", absl::StrCat(descriptor_->index()));
@@ -339,7 +339,7 @@ void ImmutableServiceGenerator::GenerateStub(io::Printer* printer) {
339339
vars["output"] = GetOutput(method);
340340
printer->Print(vars,
341341
"channel.callMethod(\n"
342-
" getDescriptor().getMethods().get($index$),\n"
342+
" getDescriptor().getMethod($index$),\n"
343343
" controller,\n"
344344
" request,\n"
345345
" $output$.getDefaultInstance(),\n"
@@ -403,7 +403,7 @@ void ImmutableServiceGenerator::GenerateBlockingStub(io::Printer* printer) {
403403
vars["output"] = GetOutput(method);
404404
printer->Print(vars,
405405
"return ($output$) channel.callBlockingMethod(\n"
406-
" getDescriptor().getMethods().get($index$),\n"
406+
" getDescriptor().getMethod($index$),\n"
407407
" controller,\n"
408408
" request,\n"
409409
" $output$.getDefaultInstance());\n");

0 commit comments

Comments
 (0)