• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Protocol Buffers - Google's data interchange format
2 // Copyright 2008 Google Inc.  All rights reserved.
3 // https://developers.google.com/protocol-buffers/
4 //
5 // Redistribution and use in source and binary forms, with or without
6 // modification, are permitted provided that the following conditions are
7 // met:
8 //
9 //     * Redistributions of source code must retain the above copyright
10 // notice, this list of conditions and the following disclaimer.
11 //     * Redistributions in binary form must reproduce the above
12 // copyright notice, this list of conditions and the following disclaimer
13 // in the documentation and/or other materials provided with the
14 // distribution.
15 //     * Neither the name of Google Inc. nor the names of its
16 // contributors may be used to endorse or promote products derived from
17 // this software without specific prior written permission.
18 //
19 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
23 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 
31 // Author: dweis@google.com (Daniel Weis)
32 //  Based on original Protocol Buffers design by
33 //  Sanjay Ghemawat, Jeff Dean, and others.
34 
35 #include <google/protobuf/compiler/java/java_message_lite.h>
36 
37 #include <algorithm>
38 #include <google/protobuf/stubs/hash.h>
39 #include <map>
40 #include <memory>
41 #ifndef _SHARED_PTR_H
42 #include <google/protobuf/stubs/shared_ptr.h>
43 #endif
44 #include <vector>
45 
46 #include <google/protobuf/compiler/java/java_context.h>
47 #include <google/protobuf/compiler/java/java_doc_comment.h>
48 #include <google/protobuf/compiler/java/java_enum_lite.h>
49 #include <google/protobuf/compiler/java/java_extension_lite.h>
50 #include <google/protobuf/compiler/java/java_generator_factory.h>
51 #include <google/protobuf/compiler/java/java_helpers.h>
52 #include <google/protobuf/compiler/java/java_message_builder.h>
53 #include <google/protobuf/compiler/java/java_message_builder_lite.h>
54 #include <google/protobuf/compiler/java/java_name_resolver.h>
55 #include <google/protobuf/io/coded_stream.h>
56 #include <google/protobuf/io/printer.h>
57 #include <google/protobuf/descriptor.pb.h>
58 #include <google/protobuf/wire_format.h>
59 #include <google/protobuf/stubs/strutil.h>
60 #include <google/protobuf/stubs/substitute.h>
61 
62 namespace google {
63 namespace protobuf {
64 namespace compiler {
65 namespace java {
66 
67 using internal::WireFormat;
68 using internal::WireFormatLite;
69 
70 namespace {
GenerateHasBits(const Descriptor * descriptor)71 bool GenerateHasBits(const Descriptor* descriptor) {
72   return SupportFieldPresence(descriptor->file()) ||
73       HasRepeatedFields(descriptor);
74 }
75 
MapValueImmutableClassdName(const Descriptor * descriptor,ClassNameResolver * name_resolver)76 string MapValueImmutableClassdName(const Descriptor* descriptor,
77                                    ClassNameResolver* name_resolver) {
78   const FieldDescriptor* value_field = descriptor->FindFieldByName("value");
79   GOOGLE_CHECK_EQ(FieldDescriptor::TYPE_MESSAGE, value_field->type());
80   return name_resolver->GetImmutableClassName(value_field->message_type());
81 }
82 }  // namespace
83 
84 // ===================================================================
ImmutableMessageLiteGenerator(const Descriptor * descriptor,Context * context)85 ImmutableMessageLiteGenerator::ImmutableMessageLiteGenerator(
86     const Descriptor* descriptor, Context* context)
87   : MessageGenerator(descriptor), context_(context),
88     name_resolver_(context->GetNameResolver()),
89     field_generators_(descriptor, context_) {
90   GOOGLE_CHECK(!HasDescriptorMethods(descriptor->file(), context->EnforceLite()))
91       << "Generator factory error: A lite message generator is used to "
92          "generate non-lite messages.";
93 }
94 
~ImmutableMessageLiteGenerator()95 ImmutableMessageLiteGenerator::~ImmutableMessageLiteGenerator() {}
96 
GenerateStaticVariables(io::Printer * printer,int * bytecode_estimate)97 void ImmutableMessageLiteGenerator::GenerateStaticVariables(
98     io::Printer* printer, int* bytecode_estimate) {
99   // Generate static members for all nested types.
100   for (int i = 0; i < descriptor_->nested_type_count(); i++) {
101     // TODO(kenton):  Reuse MessageGenerator objects?
102     ImmutableMessageLiteGenerator(descriptor_->nested_type(i), context_)
103         .GenerateStaticVariables(printer, bytecode_estimate);
104   }
105 }
106 
GenerateStaticVariableInitializers(io::Printer * printer)107 int ImmutableMessageLiteGenerator::GenerateStaticVariableInitializers(
108     io::Printer* printer) {
109   int bytecode_estimate = 0;
110   // Generate static member initializers for all nested types.
111   for (int i = 0; i < descriptor_->nested_type_count(); i++) {
112     // TODO(kenton):  Reuse MessageGenerator objects?
113     bytecode_estimate +=
114         ImmutableMessageLiteGenerator(descriptor_->nested_type(i), context_)
115             .GenerateStaticVariableInitializers(printer);
116   }
117   return bytecode_estimate;
118 }
119 
120 // ===================================================================
121 
GenerateInterface(io::Printer * printer)122 void ImmutableMessageLiteGenerator::GenerateInterface(io::Printer* printer) {
123   if (descriptor_->extension_range_count() > 0) {
124     printer->Print(
125       "public interface $classname$OrBuilder extends \n"
126       "    $extra_interfaces$\n"
127       "     com.google.protobuf.GeneratedMessageLite.\n"
128       "          ExtendableMessageOrBuilder<\n"
129       "              $classname$, $classname$.Builder> {\n",
130       "extra_interfaces", ExtraMessageOrBuilderInterfaces(descriptor_),
131       "classname", descriptor_->name());
132   } else {
133     printer->Print(
134       "public interface $classname$OrBuilder extends\n"
135       "    $extra_interfaces$\n"
136       "    com.google.protobuf.MessageLiteOrBuilder {\n",
137       "extra_interfaces", ExtraMessageOrBuilderInterfaces(descriptor_),
138       "classname", descriptor_->name());
139   }
140 
141   printer->Indent();
142     for (int i = 0; i < descriptor_->field_count(); i++) {
143       printer->Print("\n");
144       field_generators_.get(descriptor_->field(i))
145                        .GenerateInterfaceMembers(printer);
146     }
147     for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
148       printer->Print(
149           "\n"
150           "public $classname$.$oneof_capitalized_name$Case "
151           "get$oneof_capitalized_name$Case();\n",
152           "oneof_capitalized_name",
153           context_->GetOneofGeneratorInfo(
154               descriptor_->oneof_decl(i))->capitalized_name,
155           "classname",
156           context_->GetNameResolver()->GetImmutableClassName(descriptor_));
157     }
158   printer->Outdent();
159 
160   printer->Print("}\n");
161 }
162 
163 // ===================================================================
164 
Generate(io::Printer * printer)165 void ImmutableMessageLiteGenerator::Generate(io::Printer* printer) {
166   bool is_own_file =
167     descriptor_->containing_type() == NULL &&
168     MultipleJavaFiles(descriptor_->file(), /* immutable = */ true);
169 
170   map<string, string> variables;
171   variables["static"] = is_own_file ? " " : " static ";
172   variables["classname"] = descriptor_->name();
173   variables["extra_interfaces"] = ExtraMessageInterfaces(descriptor_);
174 
175   WriteMessageDocComment(printer, descriptor_);
176 
177   // The builder_type stores the super type name of the nested Builder class.
178   string builder_type;
179   if (descriptor_->extension_range_count() > 0) {
180     printer->Print(variables,
181       "public $static$final class $classname$ extends\n"
182       "    com.google.protobuf.GeneratedMessageLite.ExtendableMessage<\n"
183       "      $classname$, $classname$.Builder> implements\n"
184       "    $extra_interfaces$\n"
185       "    $classname$OrBuilder {\n");
186     builder_type = strings::Substitute(
187         "com.google.protobuf.GeneratedMessageLite.ExtendableBuilder<$0, ?>",
188         name_resolver_->GetImmutableClassName(descriptor_));
189   } else {
190     printer->Print(variables,
191         "public $static$final class $classname$ extends\n"
192         "    com.google.protobuf.GeneratedMessageLite<\n"
193         "        $classname$, $classname$.Builder> implements\n"
194         "    $extra_interfaces$\n"
195         "    $classname$OrBuilder {\n");
196 
197     builder_type = "com.google.protobuf.GeneratedMessageLite.Builder";
198   }
199   printer->Indent();
200 
201 
202   GenerateConstructor(printer);
203 
204   // Nested types
205   for (int i = 0; i < descriptor_->enum_type_count(); i++) {
206     EnumLiteGenerator(descriptor_->enum_type(i), true, context_)
207         .Generate(printer);
208   }
209 
210   for (int i = 0; i < descriptor_->nested_type_count(); i++) {
211     // Don't generate Java classes for map entry messages.
212     if (IsMapEntry(descriptor_->nested_type(i))) continue;
213     ImmutableMessageLiteGenerator messageGenerator(
214         descriptor_->nested_type(i), context_);
215     messageGenerator.GenerateInterface(printer);
216     messageGenerator.Generate(printer);
217   }
218 
219   if (GenerateHasBits(descriptor_)) {
220     // Integers for bit fields.
221     int totalBits = 0;
222     for (int i = 0; i < descriptor_->field_count(); i++) {
223       totalBits += field_generators_.get(descriptor_->field(i))
224           .GetNumBitsForMessage();
225     }
226     int totalInts = (totalBits + 31) / 32;
227     for (int i = 0; i < totalInts; i++) {
228       printer->Print("private int $bit_field_name$;\n",
229         "bit_field_name", GetBitFieldName(i));
230     }
231   }
232 
233   // oneof
234   map<string, string> vars;
235   for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
236     vars["oneof_name"] = context_->GetOneofGeneratorInfo(
237         descriptor_->oneof_decl(i))->name;
238     vars["oneof_capitalized_name"] = context_->GetOneofGeneratorInfo(
239         descriptor_->oneof_decl(i))->capitalized_name;
240     vars["oneof_index"] = SimpleItoa(descriptor_->oneof_decl(i)->index());
241     // oneofCase_ and oneof_
242     printer->Print(vars,
243       "private int $oneof_name$Case_ = 0;\n"
244       "private java.lang.Object $oneof_name$_;\n");
245     // OneofCase enum
246     printer->Print(vars,
247       "public enum $oneof_capitalized_name$Case\n"
248       "    implements com.google.protobuf.Internal.EnumLite {\n");
249     printer->Indent();
250     for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
251       const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
252       printer->Print(
253         "$field_name$($field_number$),\n",
254         "field_name",
255         ToUpper(field->name()),
256         "field_number",
257         SimpleItoa(field->number()));
258     }
259     printer->Print(
260       "$cap_oneof_name$_NOT_SET(0);\n",
261       "cap_oneof_name",
262       ToUpper(vars["oneof_name"]));
263     printer->Print(vars,
264       "private final int value;\n"
265       "private $oneof_capitalized_name$Case(int value) {\n"
266       "  this.value = value;\n"
267       "}\n");
268     printer->Print(vars,
269       "/**\n"
270       " * @deprecated Use {@link #forNumber(int)} instead.\n"
271       " */\n"
272       "@java.lang.Deprecated\n"
273       "public static $oneof_capitalized_name$Case valueOf(int value) {\n"
274       "  return forNumber(value);\n"
275       "}\n"
276       "\n"
277       "public static $oneof_capitalized_name$Case forNumber(int value) {\n"
278       "  switch (value) {\n");
279     for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
280       const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
281       printer->Print(
282         "    case $field_number$: return $field_name$;\n",
283         "field_number",
284         SimpleItoa(field->number()),
285         "field_name",
286         ToUpper(field->name()));
287     }
288     printer->Print(
289       "    case 0: return $cap_oneof_name$_NOT_SET;\n"
290       "    default: return null;\n"
291       "  }\n"
292       "}\n"
293       "public int getNumber() {\n"
294       "  return this.value;\n"
295       "}\n",
296       "cap_oneof_name", ToUpper(vars["oneof_name"]));
297     printer->Outdent();
298     printer->Print("};\n\n");
299     // oneofCase()
300     printer->Print(vars,
301       "public $oneof_capitalized_name$Case\n"
302       "get$oneof_capitalized_name$Case() {\n"
303       "  return $oneof_capitalized_name$Case.forNumber(\n"
304       "      $oneof_name$Case_);\n"
305       "}\n"
306       "\n"
307       "private void clear$oneof_capitalized_name$() {\n"
308       "  $oneof_name$Case_ = 0;\n"
309       "  $oneof_name$_ = null;\n"
310       "}\n"
311       "\n");
312   }
313 
314   // Fields
315   for (int i = 0; i < descriptor_->field_count(); i++) {
316     printer->Print("public static final int $constant_name$ = $number$;\n",
317       "constant_name", FieldConstantName(descriptor_->field(i)),
318       "number", SimpleItoa(descriptor_->field(i)->number()));
319     field_generators_.get(descriptor_->field(i)).GenerateMembers(printer);
320     printer->Print("\n");
321   }
322 
323   GenerateMessageSerializationMethods(printer);
324 
325   GenerateParseFromMethods(printer);
326   GenerateBuilder(printer);
327 
328   if (HasRequiredFields(descriptor_)) {
329     // Memoizes whether the protocol buffer is fully initialized (has all
330     // required fields). -1 means not yet computed. 0 means false and 1 means
331     // true.
332     printer->Print(
333       "private byte memoizedIsInitialized = -1;\n");
334   }
335 
336   printer->Print(
337     "protected final Object dynamicMethod(\n"
338     "    com.google.protobuf.GeneratedMessageLite.MethodToInvoke method,\n"
339     "    Object arg0, Object arg1) {\n"
340     "  switch (method) {\n"
341     "    case NEW_MUTABLE_INSTANCE: {\n"
342     "      return new $classname$();\n"
343     "    }\n",
344     "classname", name_resolver_->GetImmutableClassName(descriptor_));
345 
346   printer->Indent();
347   printer->Indent();
348 
349   printer->Print(
350     "case IS_INITIALIZED: {\n");
351   printer->Indent();
352   GenerateDynamicMethodIsInitialized(printer);
353   printer->Outdent();
354 
355   printer->Print(
356     "}\n"
357     "case MAKE_IMMUTABLE: {\n");
358 
359   printer->Indent();
360   GenerateDynamicMethodMakeImmutable(printer);
361   printer->Outdent();
362 
363   printer->Print(
364     "}\n"
365     "case NEW_BUILDER: {\n");
366 
367   printer->Indent();
368   GenerateDynamicMethodNewBuilder(printer);
369   printer->Outdent();
370 
371   printer->Print(
372     "}\n"
373     "case VISIT: {\n");
374 
375   printer->Indent();
376   GenerateDynamicMethodVisit(printer);
377   printer->Outdent();
378 
379   printer->Print(
380     "}\n"
381     "case MERGE_FROM_STREAM: {\n");
382 
383   printer->Indent();
384   GenerateDynamicMethodMergeFromStream(printer);
385   printer->Outdent();
386 
387   printer->Print(
388     "}\n"
389     "case GET_DEFAULT_INSTANCE: {\n"
390     "  return DEFAULT_INSTANCE;\n"
391     "}\n"
392     "case GET_PARSER: {\n"
393     // Generally one would use the lazy initialization holder pattern for
394     // manipulating static fields but that has exceptional cost on Android as
395     // it will generate an extra class for every message. Instead, use the
396     // double-check locking pattern which works just as well.
397     "  if (PARSER == null) {"
398     "    synchronized ($classname$.class) {\n"
399     "      if (PARSER == null) {\n"
400     "        PARSER = new DefaultInstanceBasedParser(DEFAULT_INSTANCE);\n"
401     "      }\n"
402     "    }\n"
403     "  }\n"
404     "  return PARSER;\n"
405     "}\n",
406     "classname", name_resolver_->GetImmutableClassName(descriptor_));
407 
408   printer->Outdent();
409   printer->Outdent();
410 
411   printer->Print(
412     "  }\n"
413     "  throw new UnsupportedOperationException();\n"
414     "}\n"
415     "\n",
416     "classname", name_resolver_->GetImmutableClassName(descriptor_));
417 
418   printer->Print(
419     "\n"
420     "// @@protoc_insertion_point(class_scope:$full_name$)\n",
421     "full_name", descriptor_->full_name());
422 
423 
424   // Carefully initialize the default instance in such a way that it doesn't
425   // conflict with other initialization.
426   printer->Print(
427     "private static final $classname$ DEFAULT_INSTANCE;\n",
428     "classname", name_resolver_->GetImmutableClassName(descriptor_));
429 
430   printer->Print(
431     "static {\n"
432     "  DEFAULT_INSTANCE = new $classname$();\n"
433     "  DEFAULT_INSTANCE.makeImmutable();\n"
434     "}\n"
435     "\n",
436     "classname", descriptor_->name());
437   printer->Print(
438       "public static $classname$ getDefaultInstance() {\n"
439       "  return DEFAULT_INSTANCE;\n"
440       "}\n"
441       "\n",
442       "classname", name_resolver_->GetImmutableClassName(descriptor_));
443 
444   GenerateParser(printer);
445 
446   // Extensions must be declared after the DEFAULT_INSTANCE is initialized
447   // because the DEFAULT_INSTANCE is used by the extension to lazily retrieve
448   // the outer class's FileDescriptor.
449   for (int i = 0; i < descriptor_->extension_count(); i++) {
450     ImmutableExtensionLiteGenerator(descriptor_->extension(i), context_)
451         .Generate(printer);
452   }
453 
454   printer->Outdent();
455   printer->Print("}\n\n");
456 }
457 
458 // ===================================================================
459 
460 void ImmutableMessageLiteGenerator::
GenerateMessageSerializationMethods(io::Printer * printer)461 GenerateMessageSerializationMethods(io::Printer* printer) {
462   google::protobuf::scoped_array<const FieldDescriptor * > sorted_fields(
463       SortFieldsByNumber(descriptor_));
464 
465   vector<const Descriptor::ExtensionRange*> sorted_extensions;
466   for (int i = 0; i < descriptor_->extension_range_count(); ++i) {
467     sorted_extensions.push_back(descriptor_->extension_range(i));
468   }
469   std::sort(sorted_extensions.begin(), sorted_extensions.end(),
470             ExtensionRangeOrdering());
471 
472   printer->Print(
473     "public void writeTo(com.google.protobuf.CodedOutputStream output)\n"
474     "                    throws java.io.IOException {\n");
475   printer->Indent();
476   if (HasPackedFields(descriptor_)) {
477     // writeTo(CodedOutputStream output) might be invoked without
478     // getSerializedSize() ever being called, but we need the memoized
479     // sizes in case this message has packed fields. Rather than emit checks for
480     // each packed field, just call getSerializedSize() up front.
481     // In most cases, getSerializedSize() will have already been called anyway
482     // by one of the wrapper writeTo() methods, making this call cheap.
483     printer->Print(
484       "getSerializedSize();\n");
485   }
486 
487   if (descriptor_->extension_range_count() > 0) {
488     if (descriptor_->options().message_set_wire_format()) {
489       printer->Print(
490         "com.google.protobuf.GeneratedMessageLite\n"
491         "  .ExtendableMessage<$classname$, $classname$.Builder>\n"
492         "    .ExtensionWriter extensionWriter =\n"
493         "      newMessageSetExtensionWriter();\n",
494         "classname", name_resolver_->GetImmutableClassName(descriptor_));
495     } else {
496       printer->Print(
497         "com.google.protobuf.GeneratedMessageLite\n"
498         "  .ExtendableMessage<$classname$, $classname$.Builder>\n"
499         "    .ExtensionWriter extensionWriter =\n"
500         "      newExtensionWriter();\n",
501         "classname", name_resolver_->GetImmutableClassName(descriptor_));
502     }
503   }
504 
505   // Merge the fields and the extension ranges, both sorted by field number.
506   for (int i = 0, j = 0;
507        i < descriptor_->field_count() || j < sorted_extensions.size();
508        ) {
509     if (i == descriptor_->field_count()) {
510       GenerateSerializeOneExtensionRange(printer, sorted_extensions[j++]);
511     } else if (j == sorted_extensions.size()) {
512       GenerateSerializeOneField(printer, sorted_fields[i++]);
513     } else if (sorted_fields[i]->number() < sorted_extensions[j]->start) {
514       GenerateSerializeOneField(printer, sorted_fields[i++]);
515     } else {
516       GenerateSerializeOneExtensionRange(printer, sorted_extensions[j++]);
517     }
518   }
519 
520   if (PreserveUnknownFields(descriptor_)) {
521     printer->Print(
522       "unknownFields.writeTo(output);\n");
523   }
524 
525   printer->Outdent();
526   printer->Print(
527     "}\n"
528     "\n"
529     "public int getSerializedSize() {\n"
530     "  int size = memoizedSerializedSize;\n"
531     "  if (size != -1) return size;\n"
532     "\n"
533     "  size = 0;\n");
534   printer->Indent();
535 
536   for (int i = 0; i < descriptor_->field_count(); i++) {
537     field_generators_.get(sorted_fields[i]).GenerateSerializedSizeCode(printer);
538   }
539 
540   if (descriptor_->extension_range_count() > 0) {
541     if (descriptor_->options().message_set_wire_format()) {
542       printer->Print(
543         "size += extensionsSerializedSizeAsMessageSet();\n");
544     } else {
545       printer->Print(
546         "size += extensionsSerializedSize();\n");
547     }
548   }
549 
550   if (PreserveUnknownFields(descriptor_)) {
551     printer->Print(
552       "size += unknownFields.getSerializedSize();\n");
553   }
554 
555   printer->Outdent();
556   printer->Print(
557     "  memoizedSerializedSize = size;\n"
558     "  return size;\n"
559     "}\n"
560     "\n");
561 }
562 
563 void ImmutableMessageLiteGenerator::
GenerateParseFromMethods(io::Printer * printer)564 GenerateParseFromMethods(io::Printer* printer) {
565   // Note:  These are separate from GenerateMessageSerializationMethods()
566   //   because they need to be generated even for messages that are optimized
567   //   for code size.
568   printer->Print(
569     "public static $classname$ parseFrom(\n"
570     "    com.google.protobuf.ByteString data)\n"
571     "    throws com.google.protobuf.InvalidProtocolBufferException {\n"
572     "  return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
573     "      DEFAULT_INSTANCE, data);\n"
574     "}\n"
575     "public static $classname$ parseFrom(\n"
576     "    com.google.protobuf.ByteString data,\n"
577     "    com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
578     "    throws com.google.protobuf.InvalidProtocolBufferException {\n"
579     "  return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
580     "      DEFAULT_INSTANCE, data, extensionRegistry);\n"
581     "}\n"
582     "public static $classname$ parseFrom(byte[] data)\n"
583     "    throws com.google.protobuf.InvalidProtocolBufferException {\n"
584     "  return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
585     "      DEFAULT_INSTANCE, data);\n"
586     "}\n"
587     "public static $classname$ parseFrom(\n"
588     "    byte[] data,\n"
589     "    com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
590     "    throws com.google.protobuf.InvalidProtocolBufferException {\n"
591     "  return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
592     "      DEFAULT_INSTANCE, data, extensionRegistry);\n"
593     "}\n"
594     "public static $classname$ parseFrom(java.io.InputStream input)\n"
595     "    throws java.io.IOException {\n"
596     "  return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
597     "      DEFAULT_INSTANCE, input);\n"
598     "}\n"
599     "public static $classname$ parseFrom(\n"
600     "    java.io.InputStream input,\n"
601     "    com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
602     "    throws java.io.IOException {\n"
603     "  return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
604     "      DEFAULT_INSTANCE, input, extensionRegistry);\n"
605     "}\n"
606     "public static $classname$ parseDelimitedFrom(java.io.InputStream input)\n"
607     "    throws java.io.IOException {\n"
608     "  return parseDelimitedFrom(DEFAULT_INSTANCE, input);\n"
609     "}\n"
610     "public static $classname$ parseDelimitedFrom(\n"
611     "    java.io.InputStream input,\n"
612     "    com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
613     "    throws java.io.IOException {\n"
614     "  return parseDelimitedFrom(DEFAULT_INSTANCE, input, extensionRegistry);\n"
615     "}\n"
616     "public static $classname$ parseFrom(\n"
617     "    com.google.protobuf.CodedInputStream input)\n"
618     "    throws java.io.IOException {\n"
619     "  return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
620     "      DEFAULT_INSTANCE, input);\n"
621     "}\n"
622     "public static $classname$ parseFrom(\n"
623     "    com.google.protobuf.CodedInputStream input,\n"
624     "    com.google.protobuf.ExtensionRegistryLite extensionRegistry)\n"
625     "    throws java.io.IOException {\n"
626     "  return com.google.protobuf.GeneratedMessageLite.parseFrom(\n"
627     "      DEFAULT_INSTANCE, input, extensionRegistry);\n"
628     "}\n"
629     "\n",
630     "classname", name_resolver_->GetImmutableClassName(descriptor_));
631 }
632 
GenerateSerializeOneField(io::Printer * printer,const FieldDescriptor * field)633 void ImmutableMessageLiteGenerator::GenerateSerializeOneField(
634     io::Printer* printer, const FieldDescriptor* field) {
635   field_generators_.get(field).GenerateSerializationCode(printer);
636 }
637 
GenerateSerializeOneExtensionRange(io::Printer * printer,const Descriptor::ExtensionRange * range)638 void ImmutableMessageLiteGenerator::GenerateSerializeOneExtensionRange(
639     io::Printer* printer, const Descriptor::ExtensionRange* range) {
640   printer->Print(
641     "extensionWriter.writeUntil($end$, output);\n",
642     "end", SimpleItoa(range->end));
643 }
644 
645 // ===================================================================
646 
GenerateBuilder(io::Printer * printer)647 void ImmutableMessageLiteGenerator::GenerateBuilder(io::Printer* printer) {
648   printer->Print(
649     "public static Builder newBuilder() {\n"
650     "  return DEFAULT_INSTANCE.toBuilder();\n"
651     "}\n"
652     "public static Builder newBuilder($classname$ prototype) {\n"
653     "  return DEFAULT_INSTANCE.toBuilder().mergeFrom(prototype);\n"
654     "}\n"
655     "\n",
656     "classname", name_resolver_->GetImmutableClassName(descriptor_));
657 
658   MessageBuilderLiteGenerator builderGenerator(descriptor_, context_);
659   builderGenerator.Generate(printer);
660 }
661 
662 // ===================================================================
663 
GenerateDynamicMethodIsInitialized(io::Printer * printer)664 void ImmutableMessageLiteGenerator::GenerateDynamicMethodIsInitialized(
665     io::Printer* printer) {
666   // Returns null for false, DEFAULT_INSTANCE for true.
667   if (!HasRequiredFields(descriptor_)) {
668     printer->Print("return DEFAULT_INSTANCE;\n");
669     return;
670   }
671 
672   // Don't directly compare to -1 to avoid an Android x86 JIT bug.
673   printer->Print(
674     "byte isInitialized = memoizedIsInitialized;\n"
675     "if (isInitialized == 1) return DEFAULT_INSTANCE;\n"
676     "if (isInitialized == 0) return null;\n"
677     "\n"
678     "boolean shouldMemoize = ((Boolean) arg0).booleanValue();\n");
679 
680   // Check that all required fields in this message are set.
681   // TODO(kenton):  We can optimize this when we switch to putting all the
682   //   "has" fields into a single bitfield.
683   for (int i = 0; i < descriptor_->field_count(); i++) {
684     const FieldDescriptor* field = descriptor_->field(i);
685     const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
686 
687     if (field->is_required()) {
688       printer->Print(
689         "if (!has$name$()) {\n"
690         "  if (shouldMemoize) {\n"
691         "    memoizedIsInitialized = 0;\n"
692         "  }\n"
693         "  return null;\n"
694         "}\n",
695         "name", info->capitalized_name);
696     }
697   }
698 
699   // Now check that all embedded messages are initialized.
700   for (int i = 0; i < descriptor_->field_count(); i++) {
701     const FieldDescriptor* field = descriptor_->field(i);
702     const FieldGeneratorInfo* info = context_->GetFieldGeneratorInfo(field);
703     if (GetJavaType(field) == JAVATYPE_MESSAGE &&
704         HasRequiredFields(field->message_type())) {
705       switch (field->label()) {
706         case FieldDescriptor::LABEL_REQUIRED:
707           printer->Print(
708             "if (!get$name$().isInitialized()) {\n"
709             "  if (shouldMemoize) {\n"
710             "    memoizedIsInitialized = 0;\n"
711             "  }\n"
712             "  return null;\n"
713             "}\n",
714             "type", name_resolver_->GetImmutableClassName(
715                 field->message_type()),
716             "name", info->capitalized_name);
717           break;
718         case FieldDescriptor::LABEL_OPTIONAL:
719           if (!SupportFieldPresence(descriptor_->file()) &&
720               field->containing_oneof() != NULL) {
721             const OneofDescriptor* oneof = field->containing_oneof();
722             const OneofGeneratorInfo* oneof_info =
723                 context_->GetOneofGeneratorInfo(oneof);
724             printer->Print(
725               "if ($oneof_name$Case_ == $field_number$) {\n",
726               "oneof_name", oneof_info->name,
727               "field_number", SimpleItoa(field->number()));
728           } else {
729             printer->Print(
730               "if (has$name$()) {\n",
731               "name", info->capitalized_name);
732           }
733           printer->Print(
734             "  if (!get$name$().isInitialized()) {\n"
735             "    if (shouldMemoize) {\n"
736             "      memoizedIsInitialized = 0;\n"
737             "    }\n"
738             "    return null;\n"
739             "  }\n"
740             "}\n",
741             "name", info->capitalized_name);
742           break;
743         case FieldDescriptor::LABEL_REPEATED:
744           if (IsMapEntry(field->message_type())) {
745             printer->Print(
746               "for ($type$ item : get$name$().values()) {\n"
747               "  if (!item.isInitialized()) {\n"
748               "    if (shouldMemoize) {\n"
749               "      memoizedIsInitialized = 0;\n"
750               "    }\n"
751               "    return null;\n"
752               "  }\n"
753               "}\n",
754               "type", MapValueImmutableClassdName(field->message_type(),
755                                                   name_resolver_),
756               "name", info->capitalized_name);
757           } else {
758             printer->Print(
759               "for (int i = 0; i < get$name$Count(); i++) {\n"
760               "  if (!get$name$(i).isInitialized()) {\n"
761               "    if (shouldMemoize) {\n"
762               "      memoizedIsInitialized = 0;\n"
763               "    }\n"
764               "    return null;\n"
765               "  }\n"
766               "}\n",
767               "type", name_resolver_->GetImmutableClassName(
768                   field->message_type()),
769               "name", info->capitalized_name);
770           }
771           break;
772       }
773     }
774   }
775 
776   if (descriptor_->extension_range_count() > 0) {
777     printer->Print(
778       "if (!extensionsAreInitialized()) {\n"
779       "  if (shouldMemoize) {\n"
780       "    memoizedIsInitialized = 0;\n"
781       "  }\n"
782       "  return null;\n"
783       "}\n");
784   }
785 
786   printer->Print(
787     "if (shouldMemoize) memoizedIsInitialized = 1;\n");
788 
789   printer->Print(
790     "return DEFAULT_INSTANCE;\n"
791     "\n");
792 }
793 
794 // ===================================================================
795 
GenerateDynamicMethodMakeImmutable(io::Printer * printer)796 void ImmutableMessageLiteGenerator::GenerateDynamicMethodMakeImmutable(
797     io::Printer* printer) {
798 
799   // Output generation code for each field.
800   for (int i = 0; i < descriptor_->field_count(); i++) {
801     field_generators_.get(descriptor_->field(i))
802         .GenerateDynamicMethodMakeImmutableCode(printer);
803   }
804 
805   printer->Print(
806     "return null;\n");
807 }
808 
809 // ===================================================================
810 
GenerateDynamicMethodNewBuilder(io::Printer * printer)811 void ImmutableMessageLiteGenerator::GenerateDynamicMethodNewBuilder(
812     io::Printer* printer) {
813   printer->Print(
814     "return new Builder();\n");
815 }
816 
817 // ===================================================================
818 
GenerateDynamicMethodVisit(io::Printer * printer)819 void ImmutableMessageLiteGenerator::GenerateDynamicMethodVisit(
820     io::Printer* printer) {
821   printer->Print(
822     "Visitor visitor = (Visitor) arg0;\n"
823     "$classname$ other = ($classname$) arg1;\n",
824     "classname", name_resolver_->GetImmutableClassName(descriptor_));
825 
826   for (int i = 0; i < descriptor_->field_count(); i++) {
827     if (!descriptor_->field(i)->containing_oneof()) {
828       field_generators_.get(
829           descriptor_->field(i)).GenerateVisitCode(printer);
830     }
831   }
832 
833   // Merge oneof fields.
834   for (int i = 0; i < descriptor_->oneof_decl_count(); ++i) {
835     printer->Print(
836       "switch (other.get$oneof_capitalized_name$Case()) {\n",
837       "oneof_capitalized_name",
838       context_->GetOneofGeneratorInfo(
839           descriptor_->oneof_decl(i))->capitalized_name);
840     printer->Indent();
841     for (int j = 0; j < descriptor_->oneof_decl(i)->field_count(); j++) {
842       const FieldDescriptor* field = descriptor_->oneof_decl(i)->field(j);
843       printer->Print(
844         "case $field_name$: {\n",
845         "field_name",
846         ToUpper(field->name()));
847       printer->Indent();
848       field_generators_.get(field).GenerateVisitCode(printer);
849       printer->Print(
850           "break;\n");
851       printer->Outdent();
852       printer->Print(
853           "}\n");
854     }
855     printer->Print(
856       "case $cap_oneof_name$_NOT_SET: {\n"
857       "  visitor.visitOneofNotSet($oneof_name$Case_ != 0);\n"
858       "  break;\n"
859       "}\n",
860       "cap_oneof_name",
861       ToUpper(context_->GetOneofGeneratorInfo(
862           descriptor_->oneof_decl(i))->name),
863       "oneof_name",
864       context_->GetOneofGeneratorInfo(
865           descriptor_->oneof_decl(i))->name);
866     printer->Outdent();
867     printer->Print(
868       "}\n");
869   }
870 
871   printer->Print(
872     "if (visitor == com.google.protobuf.GeneratedMessageLite.MergeFromVisitor\n"
873     "    .INSTANCE) {\n");
874   printer->Indent();
875   for (int i = 0; i < descriptor_->oneof_decl_count(); ++i) {
876     const OneofDescriptor* field = descriptor_->oneof_decl(i);
877     printer->Print(
878       "if (other.$oneof_name$Case_ != 0) {\n"
879       "  $oneof_name$Case_ = other.$oneof_name$Case_;\n"
880       "}\n",
881       "oneof_name", context_->GetOneofGeneratorInfo(field)->name);
882   }
883 
884   if (GenerateHasBits(descriptor_)) {
885     // Integers for bit fields.
886     int totalBits = 0;
887     for (int i = 0; i < descriptor_->field_count(); i++) {
888       totalBits += field_generators_.get(descriptor_->field(i))
889           .GetNumBitsForMessage();
890     }
891     int totalInts = (totalBits + 31) / 32;
892 
893     for (int i = 0; i < totalInts; i++) {
894       printer->Print(
895         "$bit_field_name$ |= other.$bit_field_name$;\n",
896         "bit_field_name", GetBitFieldName(i));
897     }
898   }
899   printer->Outdent();
900   printer->Print(
901     "}\n");
902 
903 
904   printer->Print(
905     "return this;\n");
906 }
907 
908 // ===================================================================
909 
GenerateDynamicMethodMergeFromStream(io::Printer * printer)910 void ImmutableMessageLiteGenerator::GenerateDynamicMethodMergeFromStream(
911     io::Printer* printer) {
912   printer->Print(
913       "com.google.protobuf.CodedInputStream input =\n"
914       "    (com.google.protobuf.CodedInputStream) arg0;\n"
915       "com.google.protobuf.ExtensionRegistryLite extensionRegistry =\n"
916       "    (com.google.protobuf.ExtensionRegistryLite) arg1;\n"
917       "try {\n");
918   printer->Indent();
919 
920   printer->Print(
921     "boolean done = false;\n"
922     "while (!done) {\n");
923   printer->Indent();
924 
925   printer->Print(
926     "int tag = input.readTag();\n"
927     "switch (tag) {\n");
928   printer->Indent();
929 
930   printer->Print(
931     "case 0:\n"          // zero signals EOF / limit reached
932     "  done = true;\n"
933     "  break;\n");
934 
935   if (PreserveUnknownFields(descriptor_)) {
936     if (descriptor_->extension_range_count() > 0) {
937       printer->Print(
938         "default: {\n"
939         "  if (!parseUnknownField(getDefaultInstanceForType(),\n"
940         "                         input, extensionRegistry, tag)) {\n"
941         "    done = true;\n"  // it's an endgroup tag
942         "  }\n"
943         "  break;\n"
944         "}\n");
945     } else {
946       printer->Print(
947         "default: {\n"
948         "  if (!parseUnknownField(tag, input)) {\n"
949         "    done = true;\n"  // it's an endgroup tag
950         "  }\n"
951         "  break;\n"
952         "}\n");
953     }
954   } else {
955     printer->Print(
956       "default: {\n"
957       "  if (!input.skipField(tag)) {\n"
958       "    done = true;\n"  // it's an endgroup tag
959       "  }\n"
960       "  break;\n"
961       "}\n");
962   }
963 
964   google::protobuf::scoped_array<const FieldDescriptor * > sorted_fields(
965       SortFieldsByNumber(descriptor_));
966   for (int i = 0; i < descriptor_->field_count(); i++) {
967     const FieldDescriptor* field = sorted_fields[i];
968     uint32 tag = WireFormatLite::MakeTag(field->number(),
969       WireFormat::WireTypeForFieldType(field->type()));
970 
971     printer->Print(
972       "case $tag$: {\n",
973       "tag", SimpleItoa(tag));
974     printer->Indent();
975 
976     field_generators_.get(field).GenerateParsingCode(printer);
977 
978     printer->Outdent();
979     printer->Print(
980       "  break;\n"
981       "}\n");
982 
983     if (field->is_packable()) {
984       // To make packed = true wire compatible, we generate parsing code from a
985       // packed version of this field regardless of field->options().packed().
986       uint32 packed_tag = WireFormatLite::MakeTag(field->number(),
987         WireFormatLite::WIRETYPE_LENGTH_DELIMITED);
988       printer->Print(
989         "case $tag$: {\n",
990         "tag", SimpleItoa(packed_tag));
991       printer->Indent();
992 
993       field_generators_.get(field).GenerateParsingCodeFromPacked(printer);
994 
995       printer->Outdent();
996       printer->Print(
997         "  break;\n"
998         "}\n");
999     }
1000   }
1001 
1002   printer->Outdent();
1003   printer->Outdent();
1004   printer->Print(
1005       "  }\n"     // switch (tag)
1006       "}\n");     // while (!done)
1007 
1008   printer->Outdent();
1009   printer->Print(
1010       "} catch (com.google.protobuf.InvalidProtocolBufferException e) {\n"
1011       "  throw new RuntimeException(e.setUnfinishedMessage(this));\n"
1012       "} catch (java.io.IOException e) {\n"
1013       "  throw new RuntimeException(\n"
1014       "      new com.google.protobuf.InvalidProtocolBufferException(\n"
1015       "          e.getMessage()).setUnfinishedMessage(this));\n"
1016       "} finally {\n");
1017   printer->Indent();
1018 
1019   printer->Outdent();
1020   printer->Print(
1021       "}\n");     // finally
1022 }
1023 
1024 // ===================================================================
1025 
1026 namespace {
CheckHasBitsForEqualsAndHashCode(const FieldDescriptor * field)1027 bool CheckHasBitsForEqualsAndHashCode(const FieldDescriptor* field) {
1028   if (field->is_repeated()) {
1029     return false;
1030   }
1031   if (SupportFieldPresence(field->file())) {
1032     return true;
1033   }
1034   return GetJavaType(field) == JAVATYPE_MESSAGE &&
1035       field->containing_oneof() == NULL;
1036 }
1037 }  // namespace
1038 
1039 // ===================================================================
1040 
1041 void ImmutableMessageLiteGenerator::
GenerateExtensionRegistrationCode(io::Printer * printer)1042 GenerateExtensionRegistrationCode(io::Printer* printer) {
1043   for (int i = 0; i < descriptor_->extension_count(); i++) {
1044     ImmutableExtensionLiteGenerator(descriptor_->extension(i), context_)
1045       .GenerateRegistrationCode(printer);
1046   }
1047 
1048   for (int i = 0; i < descriptor_->nested_type_count(); i++) {
1049     ImmutableMessageLiteGenerator(descriptor_->nested_type(i), context_)
1050       .GenerateExtensionRegistrationCode(printer);
1051   }
1052 }
1053 
1054 // ===================================================================
1055 void ImmutableMessageLiteGenerator::
GenerateConstructor(io::Printer * printer)1056 GenerateConstructor(io::Printer* printer) {
1057   printer->Print(
1058       "private $classname$() {\n",
1059       "classname", descriptor_->name());
1060   printer->Indent();
1061 
1062   // Initialize all fields to default.
1063   GenerateInitializers(printer);
1064 
1065   printer->Outdent();
1066   printer->Print(
1067       "}\n");
1068 }
1069 
1070 // ===================================================================
GenerateParser(io::Printer * printer)1071 void ImmutableMessageLiteGenerator::GenerateParser(io::Printer* printer) {
1072   printer->Print(
1073       "private static volatile com.google.protobuf.Parser<$classname$> PARSER;\n"
1074       "\n"
1075       "public static com.google.protobuf.Parser<$classname$> parser() {\n"
1076       "  return DEFAULT_INSTANCE.getParserForType();\n"
1077       "}\n",
1078       "classname", descriptor_->name());
1079 }
1080 
1081 // ===================================================================
GenerateInitializers(io::Printer * printer)1082 void ImmutableMessageLiteGenerator::GenerateInitializers(io::Printer* printer) {
1083   for (int i = 0; i < descriptor_->field_count(); i++) {
1084     if (!descriptor_->field(i)->containing_oneof()) {
1085       field_generators_.get(descriptor_->field(i))
1086           .GenerateInitializationCode(printer);
1087     }
1088   }
1089 }
1090 
1091 }  // namespace java
1092 }  // namespace compiler
1093 }  // namespace protobuf
1094 }  // namespace google
1095