• 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 package com.google.protobuf;
32 
33 import com.google.protobuf.AbstractMessageLite.Builder.LimitedInputStream;
34 import com.google.protobuf.Internal.BooleanList;
35 import com.google.protobuf.Internal.DoubleList;
36 import com.google.protobuf.Internal.FloatList;
37 import com.google.protobuf.Internal.IntList;
38 import com.google.protobuf.Internal.LongList;
39 import com.google.protobuf.Internal.ProtobufList;
40 import com.google.protobuf.WireFormat.FieldType;
41 import java.io.IOException;
42 import java.io.InputStream;
43 import java.io.ObjectStreamException;
44 import java.io.Serializable;
45 import java.lang.reflect.InvocationTargetException;
46 import java.lang.reflect.Method;
47 import java.nio.ByteBuffer;
48 import java.util.ArrayList;
49 import java.util.Collections;
50 import java.util.Iterator;
51 import java.util.List;
52 import java.util.Map;
53 import java.util.concurrent.ConcurrentHashMap;
54 
55 /**
56  * Lite version of {@link GeneratedMessage}.
57  *
58  * @author kenton@google.com Kenton Varda
59  */
60 public abstract class GeneratedMessageLite<
61         MessageType extends GeneratedMessageLite<MessageType, BuilderType>,
62         BuilderType extends GeneratedMessageLite.Builder<MessageType, BuilderType>>
63     extends AbstractMessageLite<MessageType, BuilderType> {
64 
65   /* For use by lite runtime only */
66   static final int UNINITIALIZED_SERIALIZED_SIZE = 0x7FFFFFFF;
67   private static final int MUTABLE_FLAG_MASK = 0x80000000;
68   private static final int MEMOIZED_SERIALIZED_SIZE_MASK = 0x7FFFFFFF;
69 
70   /**
71    * We use the high bit of memoizedSerializedSize as the explicit mutability flag. It didn't make
72    * sense to have negative sizes anyway. Messages start as mutable.
73    *
74    * <p>Adding a standalone boolean would have added 8 bytes to every message instance.
75    *
76    * <p>We also reserve 0x7FFFFFFF as the "uninitialized" value.
77    */
78   private int memoizedSerializedSize = MUTABLE_FLAG_MASK | UNINITIALIZED_SERIALIZED_SIZE;
79 
80   /* For use by the runtime only */
81   static final int UNINITIALIZED_HASH_CODE = 0;
82 
83   /** For use by generated code only. Lazily initialized to reduce allocations. */
84   protected UnknownFieldSetLite unknownFields = UnknownFieldSetLite.getDefaultInstance();
85 
isMutable()86   boolean isMutable() {
87     return (memoizedSerializedSize & MUTABLE_FLAG_MASK) != 0;
88   }
89 
markImmutable()90   void markImmutable() {
91     memoizedSerializedSize &= ~MUTABLE_FLAG_MASK;
92   }
93 
getMemoizedHashCode()94   int getMemoizedHashCode() {
95     return memoizedHashCode;
96   }
97 
setMemoizedHashCode(int value)98   void setMemoizedHashCode(int value) {
99     memoizedHashCode = value;
100   }
101 
clearMemoizedHashCode()102   void clearMemoizedHashCode() {
103     memoizedHashCode = UNINITIALIZED_HASH_CODE;
104   }
105 
hashCodeIsNotMemoized()106   boolean hashCodeIsNotMemoized() {
107     return UNINITIALIZED_HASH_CODE == getMemoizedHashCode();
108   }
109 
110   @Override
111   @SuppressWarnings("unchecked") // Guaranteed by runtime.
getParserForType()112   public final Parser<MessageType> getParserForType() {
113     return (Parser<MessageType>) dynamicMethod(MethodToInvoke.GET_PARSER);
114   }
115 
116   @Override
117   @SuppressWarnings("unchecked") // Guaranteed by runtime.
getDefaultInstanceForType()118   public final MessageType getDefaultInstanceForType() {
119     return (MessageType) dynamicMethod(MethodToInvoke.GET_DEFAULT_INSTANCE);
120   }
121 
122   @Override
123   @SuppressWarnings("unchecked") // Guaranteed by runtime.
newBuilderForType()124   public final BuilderType newBuilderForType() {
125     return (BuilderType) dynamicMethod(MethodToInvoke.NEW_BUILDER);
126   }
127 
newMutableInstance()128   MessageType newMutableInstance() {
129     return (MessageType) dynamicMethod(MethodToInvoke.NEW_MUTABLE_INSTANCE);
130   }
131 
132   /**
133    * A reflective toString function. This is primarily intended as a developer aid, while keeping
134    * binary size down. The first line of the {@code toString()} representation includes a commented
135    * version of {@code super.toString()} to act as an indicator that this should not be relied on
136    * for comparisons.
137    *
138    * <p>NOTE: This method relies on the field getter methods not being stripped or renamed by
139    * proguard. If they are, the fields will not be included in the returned string representation.
140    *
141    * <p>NOTE: This implementation is liable to change in the future, and should not be relied on in
142    * code.
143    */
144   @Override
toString()145   public String toString() {
146     return MessageLiteToString.toString(this, super.toString());
147   }
148 
149   @SuppressWarnings("unchecked") // Guaranteed by runtime
150   @Override
hashCode()151   public int hashCode() {
152     if (isMutable()) {
153       return computeHashCode();
154     }
155 
156     if (hashCodeIsNotMemoized()) {
157       setMemoizedHashCode(computeHashCode());
158     }
159 
160     return getMemoizedHashCode();
161   }
162 
computeHashCode()163   int computeHashCode() {
164     return Protobuf.getInstance().schemaFor(this).hashCode(this);
165   }
166 
167   @SuppressWarnings("unchecked") // Guaranteed by isInstance + runtime
168   @Override
equals( Object other)169   public boolean equals(
170           Object other) {
171     if (this == other) {
172       return true;
173     }
174 
175     if (other == null) {
176       return false;
177     }
178 
179     if (this.getClass() != other.getClass()) {
180       return false;
181     }
182 
183     return Protobuf.getInstance().schemaFor(this).equals(this, (MessageType) other);
184   }
185 
186   // The general strategy for unknown fields is to use an UnknownFieldSetLite that is treated as
187   // mutable during the parsing constructor and immutable after. This allows us to avoid
188   // any unnecessary intermediary allocations while reducing the generated code size.
189 
190   /** Lazily initializes unknown fields. */
ensureUnknownFieldsInitialized()191   private final void ensureUnknownFieldsInitialized() {
192     if (unknownFields == UnknownFieldSetLite.getDefaultInstance()) {
193       unknownFields = UnknownFieldSetLite.newInstance();
194     }
195   }
196 
197   /**
198    * Called by subclasses to parse an unknown field. For use by generated code only.
199    *
200    * @return {@code true} unless the tag is an end-group tag.
201    */
parseUnknownField(int tag, CodedInputStream input)202   protected boolean parseUnknownField(int tag, CodedInputStream input) throws IOException {
203     // This will avoid the allocation of unknown fields when a group tag is encountered.
204     if (WireFormat.getTagWireType(tag) == WireFormat.WIRETYPE_END_GROUP) {
205       return false;
206     }
207 
208     ensureUnknownFieldsInitialized();
209     return unknownFields.mergeFieldFrom(tag, input);
210   }
211 
212   /** Called by subclasses to parse an unknown field. For use by generated code only. */
mergeVarintField(int tag, int value)213   protected void mergeVarintField(int tag, int value) {
214     ensureUnknownFieldsInitialized();
215     unknownFields.mergeVarintField(tag, value);
216   }
217 
218   /** Called by subclasses to parse an unknown field. For use by generated code only. */
mergeLengthDelimitedField(int fieldNumber, ByteString value)219   protected void mergeLengthDelimitedField(int fieldNumber, ByteString value) {
220     ensureUnknownFieldsInitialized();
221     unknownFields.mergeLengthDelimitedField(fieldNumber, value);
222   }
223 
224   /** Called by subclasses to complete parsing. For use by generated code only. */
makeImmutable()225   protected void makeImmutable() {
226     Protobuf.getInstance().schemaFor(this).makeImmutable(this);
227     markImmutable();
228   }
229 
230   protected final <
231           MessageType extends GeneratedMessageLite<MessageType, BuilderType>,
232           BuilderType extends GeneratedMessageLite.Builder<MessageType, BuilderType>>
createBuilder()233       BuilderType createBuilder() {
234     return (BuilderType) dynamicMethod(MethodToInvoke.NEW_BUILDER);
235   }
236 
237   protected final <
238           MessageType extends GeneratedMessageLite<MessageType, BuilderType>,
239           BuilderType extends GeneratedMessageLite.Builder<MessageType, BuilderType>>
createBuilder(MessageType prototype)240       BuilderType createBuilder(MessageType prototype) {
241     return ((BuilderType) createBuilder()).mergeFrom(prototype);
242   }
243 
244   @Override
isInitialized()245   public final boolean isInitialized() {
246     return isInitialized((MessageType) this, Boolean.TRUE);
247   }
248 
249   @Override
250   @SuppressWarnings("unchecked")
toBuilder()251   public final BuilderType toBuilder() {
252     BuilderType builder = (BuilderType) dynamicMethod(MethodToInvoke.NEW_BUILDER);
253     return builder.mergeFrom((MessageType) this);
254   }
255 
256   /**
257    * Defines which method path to invoke in {@link GeneratedMessageLite
258    * #dynamicMethod(MethodToInvoke, Object...)}.
259    *
260    * <p>For use by generated code only.
261    */
262   public static enum MethodToInvoke {
263     // Rely on/modify instance state
264     GET_MEMOIZED_IS_INITIALIZED,
265     SET_MEMOIZED_IS_INITIALIZED,
266 
267     // Rely on static state
268     BUILD_MESSAGE_INFO,
269     NEW_MUTABLE_INSTANCE,
270     NEW_BUILDER,
271     GET_DEFAULT_INSTANCE,
272     GET_PARSER;
273   }
274 
275   /**
276    * A method that implements different types of operations described in {@link MethodToInvoke}.
277    * These different kinds of operations are required to implement message-level operations for
278    * builders in the runtime. This method bundles those operations to reduce the generated methods
279    * count.
280    *
281    * <ul>
282    *   <li>{@code NEW_INSTANCE} returns a new instance of the protocol buffer that has not yet been
283    *       made immutable. See {@code MAKE_IMMUTABLE}.
284    *   <li>{@code IS_INITIALIZED} returns {@code null} for false and the default instance for true.
285    *       It doesn't use or modify any memoized value.
286    *   <li>{@code GET_MEMOIZED_IS_INITIALIZED} returns the memoized {@code isInitialized} byte
287    *       value.
288    *   <li>{@code SET_MEMOIZED_IS_INITIALIZED} sets the memoized {@code isInitialized} byte value to
289    *       1 if the first parameter is not null, or to 0 if the first parameter is null.
290    *   <li>{@code NEW_BUILDER} returns a {@code BuilderType} instance.
291    * </ul>
292    *
293    * This method, plus the implementation of the Builder, enables the Builder class to be proguarded
294    * away entirely on Android.
295    *
296    * <p>For use by generated code only.
297    */
dynamicMethod(MethodToInvoke method, Object arg0, Object arg1)298   protected abstract Object dynamicMethod(MethodToInvoke method, Object arg0, Object arg1);
299 
300   /** Same as {@link #dynamicMethod(MethodToInvoke, Object, Object)} with {@code null} padding. */
dynamicMethod(MethodToInvoke method, Object arg0)301   protected Object dynamicMethod(MethodToInvoke method, Object arg0) {
302     return dynamicMethod(method, arg0, null);
303   }
304 
305   /** Same as {@link #dynamicMethod(MethodToInvoke, Object, Object)} with {@code null} padding. */
dynamicMethod(MethodToInvoke method)306   protected Object dynamicMethod(MethodToInvoke method) {
307     return dynamicMethod(method, null, null);
308   }
309 
clearMemoizedSerializedSize()310   void clearMemoizedSerializedSize() {
311     setMemoizedSerializedSize(UNINITIALIZED_SERIALIZED_SIZE);
312   }
313 
314   @Override
getMemoizedSerializedSize()315   int getMemoizedSerializedSize() {
316     return memoizedSerializedSize & MEMOIZED_SERIALIZED_SIZE_MASK;
317   }
318 
319   @Override
setMemoizedSerializedSize(int size)320   void setMemoizedSerializedSize(int size) {
321     if (size < 0) {
322       throw new IllegalStateException("serialized size must be non-negative, was " + size);
323     }
324     memoizedSerializedSize =
325         (memoizedSerializedSize & MUTABLE_FLAG_MASK) | (size & MEMOIZED_SERIALIZED_SIZE_MASK);
326   }
327 
328   @Override
writeTo(CodedOutputStream output)329   public void writeTo(CodedOutputStream output) throws IOException {
330     Protobuf.getInstance()
331         .schemaFor(this)
332         .writeTo(this, CodedOutputStreamWriter.forCodedOutput(output));
333   }
334 
335   @Override
getSerializedSize(Schema schema)336   int getSerializedSize(Schema schema) {
337     if (isMutable()) {
338       // The serialized size should never be memoized for mutable instances.
339       int size = computeSerializedSize(schema);
340       if (size < 0) {
341         throw new IllegalStateException("serialized size must be non-negative, was " + size);
342       }
343       return size;
344     }
345 
346     // If memoizedSerializedSize has already been set, return it.
347     if (getMemoizedSerializedSize() != UNINITIALIZED_SERIALIZED_SIZE) {
348       return getMemoizedSerializedSize();
349     }
350 
351     // Need to compute and memoize the serialized size.
352     int size = computeSerializedSize(schema);
353     setMemoizedSerializedSize(size);
354     return size;
355   }
356 
357   @Override
getSerializedSize()358   public int getSerializedSize() {
359     // Calling this with 'null' to delay schema lookup in case the serializedSize is already
360     // memoized.
361     return getSerializedSize(null);
362     }
363 
computeSerializedSize(Schema<?> nullableSchema)364   private int computeSerializedSize(Schema<?> nullableSchema) {
365     if (nullableSchema == null) {
366       return Protobuf.getInstance().schemaFor(this).getSerializedSize(this);
367     } else {
368       return ((Schema<GeneratedMessageLite<MessageType, BuilderType>>) nullableSchema)
369           .getSerializedSize(this);
370      }
371   }
372 
373   /** Constructs a {@link MessageInfo} for this message type. */
buildMessageInfo()374   Object buildMessageInfo() throws Exception {
375     return dynamicMethod(MethodToInvoke.BUILD_MESSAGE_INFO);
376   }
377 
378   private static Map<Object, GeneratedMessageLite<?, ?>> defaultInstanceMap =
379       new ConcurrentHashMap<Object, GeneratedMessageLite<?, ?>>();
380 
381   @SuppressWarnings("unchecked")
getDefaultInstance(Class<T> clazz)382   static <T extends GeneratedMessageLite<?, ?>> T getDefaultInstance(Class<T> clazz) {
383     T result = (T) defaultInstanceMap.get(clazz);
384     if (result == null) {
385       // Foo.class does not initialize the class so we need to force the initialization in order to
386       // get the default instance registered.
387       try {
388         Class.forName(clazz.getName(), true, clazz.getClassLoader());
389       } catch (ClassNotFoundException e) {
390         throw new IllegalStateException("Class initialization cannot fail.", e);
391       }
392       result = (T) defaultInstanceMap.get(clazz);
393     }
394     if (result == null) {
395       // On some Samsung devices, this still doesn't return a valid value for some reason. We add a
396       // reflective fallback to keep the device running. See b/114675342.
397       result = (T) UnsafeUtil.allocateInstance(clazz).getDefaultInstanceForType();
398       // A sanity check to ensure that <clinit> was actually invoked.
399       if (result == null) {
400         throw new IllegalStateException();
401       }
402       defaultInstanceMap.put(clazz, result);
403     }
404     return result;
405   }
406 
registerDefaultInstance( Class<T> clazz, T defaultInstance)407   protected static <T extends GeneratedMessageLite<?, ?>> void registerDefaultInstance(
408       Class<T> clazz, T defaultInstance) {
409     defaultInstanceMap.put(clazz, defaultInstance);
410     defaultInstance.makeImmutable();
411   }
412 
newMessageInfo( MessageLite defaultInstance, String info, Object[] objects)413   protected static Object newMessageInfo(
414       MessageLite defaultInstance, String info, Object[] objects) {
415     return new RawMessageInfo(defaultInstance, info, objects);
416   }
417 
418   /**
419    * Merge some unknown fields into the {@link UnknownFieldSetLite} for this message.
420    *
421    * <p>For use by generated code only.
422    */
mergeUnknownFields(UnknownFieldSetLite unknownFields)423   protected final void mergeUnknownFields(UnknownFieldSetLite unknownFields) {
424     this.unknownFields = UnknownFieldSetLite.mutableCopyOf(this.unknownFields, unknownFields);
425   }
426 
427   @SuppressWarnings("unchecked")
428   public abstract static class Builder<
429           MessageType extends GeneratedMessageLite<MessageType, BuilderType>,
430           BuilderType extends Builder<MessageType, BuilderType>>
431       extends AbstractMessageLite.Builder<MessageType, BuilderType> {
432 
433     private final MessageType defaultInstance;
434     protected MessageType instance;
435 
Builder(MessageType defaultInstance)436     protected Builder(MessageType defaultInstance) {
437       this.defaultInstance = defaultInstance;
438       if (defaultInstance.isMutable()) {
439         throw new IllegalArgumentException("Default instance must be immutable.");
440       }
441       // this.instance should be set to defaultInstance but some tests rely on newBuilder().build()
442       // creating unique instances.
443       this.instance = newMutableInstance();
444     }
445 
newMutableInstance()446     private MessageType newMutableInstance() {
447       return defaultInstance.newMutableInstance();
448     }
449 
450     /**
451      * Called before any method that would mutate the builder to ensure that it correctly copies any
452      * state before the write happens to preserve immutability guarantees.
453      */
copyOnWrite()454     protected final void copyOnWrite() {
455       if (!instance.isMutable()) {
456         copyOnWriteInternal();
457       }
458     }
459 
copyOnWriteInternal()460     protected void copyOnWriteInternal() {
461       MessageType newInstance = newMutableInstance();
462       mergeFromInstance(newInstance, instance);
463       instance = newInstance;
464     }
465 
466     @Override
isInitialized()467     public final boolean isInitialized() {
468       return GeneratedMessageLite.isInitialized(instance, /* shouldMemoize= */ false);
469     }
470 
471     @Override
clear()472     public final BuilderType clear() {
473       // No need to copy on write since we're dropping the instance anyway.
474       if (defaultInstance.isMutable()) {
475         throw new IllegalArgumentException("Default instance must be immutable.");
476       }
477       instance = newMutableInstance(); // should be defaultInstance;
478       return (BuilderType) this;
479     }
480 
481     @Override
clone()482     public BuilderType clone() {
483       BuilderType builder = (BuilderType) getDefaultInstanceForType().newBuilderForType();
484       builder.instance = buildPartial();
485       return builder;
486     }
487 
488     @Override
buildPartial()489     public MessageType buildPartial() {
490       if (!instance.isMutable()) {
491         return instance;
492       }
493 
494       instance.makeImmutable();
495       return instance;
496     }
497 
498     @Override
build()499     public final MessageType build() {
500       MessageType result = buildPartial();
501       if (!result.isInitialized()) {
502         throw newUninitializedMessageException(result);
503       }
504       return result;
505     }
506 
507     @Override
internalMergeFrom(MessageType message)508     protected BuilderType internalMergeFrom(MessageType message) {
509       return mergeFrom(message);
510     }
511 
512     /** All subclasses implement this. */
mergeFrom(MessageType message)513     public BuilderType mergeFrom(MessageType message) {
514       if (getDefaultInstanceForType().equals(message)) {
515         return (BuilderType) this;
516       }
517       copyOnWrite();
518       mergeFromInstance(instance, message);
519       return (BuilderType) this;
520     }
521 
mergeFromInstance(MessageType dest, MessageType src)522     private static <MessageType> void mergeFromInstance(MessageType dest, MessageType src) {
523       Protobuf.getInstance().schemaFor(dest).mergeFrom(dest, src);
524     }
525 
526     @Override
getDefaultInstanceForType()527     public MessageType getDefaultInstanceForType() {
528       return defaultInstance;
529     }
530 
531     @Override
mergeFrom( byte[] input, int offset, int length, ExtensionRegistryLite extensionRegistry)532     public BuilderType mergeFrom(
533         byte[] input, int offset, int length, ExtensionRegistryLite extensionRegistry)
534         throws InvalidProtocolBufferException {
535       copyOnWrite();
536       try {
537         Protobuf.getInstance().schemaFor(instance).mergeFrom(
538             instance, input, offset, offset + length,
539             new ArrayDecoders.Registers(extensionRegistry));
540       } catch (InvalidProtocolBufferException e) {
541         throw e;
542       } catch (IndexOutOfBoundsException e) {
543         throw InvalidProtocolBufferException.truncatedMessage();
544       } catch (IOException e) {
545         throw new RuntimeException("Reading from byte array should not throw IOException.", e);
546       }
547       return (BuilderType) this;
548     }
549 
550     @Override
mergeFrom( byte[] input, int offset, int length)551     public BuilderType mergeFrom(
552         byte[] input, int offset, int length)
553         throws InvalidProtocolBufferException {
554       return mergeFrom(input, offset, length, ExtensionRegistryLite.getEmptyRegistry());
555     }
556 
557     @Override
mergeFrom( com.google.protobuf.CodedInputStream input, com.google.protobuf.ExtensionRegistryLite extensionRegistry)558     public BuilderType mergeFrom(
559         com.google.protobuf.CodedInputStream input,
560         com.google.protobuf.ExtensionRegistryLite extensionRegistry)
561         throws IOException {
562       copyOnWrite();
563       try {
564         // TODO(yilunchong): Try to make input with type CodedInputStream.ArrayDecoder use
565         // fast path.
566         Protobuf.getInstance().schemaFor(instance).mergeFrom(
567             instance, CodedInputStreamReader.forCodedInput(input), extensionRegistry);
568       } catch (RuntimeException e) {
569         if (e.getCause() instanceof IOException) {
570           throw (IOException) e.getCause();
571         }
572         throw e;
573       }
574       return (BuilderType) this;
575     }
576   }
577 
578 
579   // =================================================================
580   // Extensions-related stuff
581 
582   /** Lite equivalent of {@link com.google.protobuf.GeneratedMessage.ExtendableMessageOrBuilder}. */
583   public interface ExtendableMessageOrBuilder<
584           MessageType extends ExtendableMessage<MessageType, BuilderType>,
585           BuilderType extends ExtendableBuilder<MessageType, BuilderType>>
586       extends MessageLiteOrBuilder {
587 
588     /** Check if a singular extension is present. */
hasExtension(ExtensionLite<MessageType, Type> extension)589     <Type> boolean hasExtension(ExtensionLite<MessageType, Type> extension);
590 
591     /** Get the number of elements in a repeated extension. */
getExtensionCount(ExtensionLite<MessageType, List<Type>> extension)592     <Type> int getExtensionCount(ExtensionLite<MessageType, List<Type>> extension);
593 
594     /** Get the value of an extension. */
getExtension(ExtensionLite<MessageType, Type> extension)595     <Type> Type getExtension(ExtensionLite<MessageType, Type> extension);
596 
597     /** Get one element of a repeated extension. */
getExtension(ExtensionLite<MessageType, List<Type>> extension, int index)598     <Type> Type getExtension(ExtensionLite<MessageType, List<Type>> extension, int index);
599   }
600 
601   /** Lite equivalent of {@link GeneratedMessage.ExtendableMessage}. */
602   public abstract static class ExtendableMessage<
603           MessageType extends ExtendableMessage<MessageType, BuilderType>,
604           BuilderType extends ExtendableBuilder<MessageType, BuilderType>>
605       extends GeneratedMessageLite<MessageType, BuilderType>
606       implements ExtendableMessageOrBuilder<MessageType, BuilderType> {
607 
608     /** Represents the set of extensions on this message. For use by generated code only. */
609     protected FieldSet<ExtensionDescriptor> extensions = FieldSet.emptySet();
610 
611     @SuppressWarnings("unchecked")
mergeExtensionFields(final MessageType other)612     protected final void mergeExtensionFields(final MessageType other) {
613       if (extensions.isImmutable()) {
614         extensions = extensions.clone();
615       }
616       extensions.mergeFrom(((ExtendableMessage) other).extensions);
617     }
618 
619     /**
620      * Parse an unknown field or an extension. For use by generated code only.
621      *
622      * <p>For use by generated code only.
623      *
624      * @return {@code true} unless the tag is an end-group tag.
625      */
parseUnknownField( MessageType defaultInstance, CodedInputStream input, ExtensionRegistryLite extensionRegistry, int tag)626     protected <MessageType extends MessageLite> boolean parseUnknownField(
627         MessageType defaultInstance,
628         CodedInputStream input,
629         ExtensionRegistryLite extensionRegistry,
630         int tag)
631         throws IOException {
632       int fieldNumber = WireFormat.getTagFieldNumber(tag);
633 
634       // TODO(dweis): How much bytecode would be saved by not requiring the generated code to
635       //     provide the default instance?
636       GeneratedExtension<MessageType, ?> extension =
637           extensionRegistry.findLiteExtensionByNumber(defaultInstance, fieldNumber);
638 
639       return parseExtension(input, extensionRegistry, extension, tag, fieldNumber);
640     }
641 
parseExtension( CodedInputStream input, ExtensionRegistryLite extensionRegistry, GeneratedExtension<?, ?> extension, int tag, int fieldNumber)642     private boolean parseExtension(
643         CodedInputStream input,
644         ExtensionRegistryLite extensionRegistry,
645         GeneratedExtension<?, ?> extension,
646         int tag,
647         int fieldNumber)
648         throws IOException {
649       int wireType = WireFormat.getTagWireType(tag);
650       boolean unknown = false;
651       boolean packed = false;
652       if (extension == null) {
653         unknown = true; // Unknown field.
654       } else if (wireType
655           == FieldSet.getWireFormatForFieldType(
656               extension.descriptor.getLiteType(), /* isPacked= */ false)) {
657         packed = false; // Normal, unpacked value.
658       } else if (extension.descriptor.isRepeated
659           && extension.descriptor.type.isPackable()
660           && wireType
661               == FieldSet.getWireFormatForFieldType(
662                   extension.descriptor.getLiteType(), /* isPacked= */ true)) {
663         packed = true; // Packed value.
664       } else {
665         unknown = true; // Wrong wire type.
666       }
667 
668       if (unknown) { // Unknown field or wrong wire type.  Skip.
669         return parseUnknownField(tag, input);
670       }
671 
672       ensureExtensionsAreMutable();
673 
674       if (packed) {
675         int length = input.readRawVarint32();
676         int limit = input.pushLimit(length);
677         if (extension.descriptor.getLiteType() == WireFormat.FieldType.ENUM) {
678           while (input.getBytesUntilLimit() > 0) {
679             int rawValue = input.readEnum();
680             Object value = extension.descriptor.getEnumType().findValueByNumber(rawValue);
681             if (value == null) {
682               // If the number isn't recognized as a valid value for this
683               // enum, drop it (don't even add it to unknownFields).
684               return true;
685             }
686             extensions.addRepeatedField(
687                 extension.descriptor, extension.singularToFieldSetType(value));
688           }
689         } else {
690           while (input.getBytesUntilLimit() > 0) {
691             Object value =
692                 FieldSet.readPrimitiveField(
693                     input, extension.descriptor.getLiteType(), /*checkUtf8=*/ false);
694             extensions.addRepeatedField(extension.descriptor, value);
695           }
696         }
697         input.popLimit(limit);
698       } else {
699         Object value;
700         switch (extension.descriptor.getLiteJavaType()) {
701           case MESSAGE:
702             {
703               MessageLite.Builder subBuilder = null;
704               if (!extension.descriptor.isRepeated()) {
705                 MessageLite existingValue = (MessageLite) extensions.getField(extension.descriptor);
706                 if (existingValue != null) {
707                   subBuilder = existingValue.toBuilder();
708                 }
709               }
710               if (subBuilder == null) {
711                 subBuilder = extension.getMessageDefaultInstance().newBuilderForType();
712               }
713               if (extension.descriptor.getLiteType() == WireFormat.FieldType.GROUP) {
714                 input.readGroup(extension.getNumber(), subBuilder, extensionRegistry);
715               } else {
716                 input.readMessage(subBuilder, extensionRegistry);
717               }
718               value = subBuilder.build();
719               break;
720             }
721           case ENUM:
722             int rawValue = input.readEnum();
723             value = extension.descriptor.getEnumType().findValueByNumber(rawValue);
724             // If the number isn't recognized as a valid value for this enum,
725             // write it to unknown fields object.
726             if (value == null) {
727               mergeVarintField(fieldNumber, rawValue);
728               return true;
729             }
730             break;
731           default:
732             value =
733                 FieldSet.readPrimitiveField(
734                     input, extension.descriptor.getLiteType(), /*checkUtf8=*/ false);
735             break;
736         }
737 
738         if (extension.descriptor.isRepeated()) {
739           extensions.addRepeatedField(
740               extension.descriptor, extension.singularToFieldSetType(value));
741         } else {
742           extensions.setField(extension.descriptor, extension.singularToFieldSetType(value));
743         }
744       }
745       return true;
746     }
747 
748     /**
749      * Parse an unknown field or an extension. For use by generated code only.
750      *
751      * <p>For use by generated code only.
752      *
753      * @return {@code true} unless the tag is an end-group tag.
754      */
parseUnknownFieldAsMessageSet( MessageType defaultInstance, CodedInputStream input, ExtensionRegistryLite extensionRegistry, int tag)755     protected <MessageType extends MessageLite> boolean parseUnknownFieldAsMessageSet(
756         MessageType defaultInstance,
757         CodedInputStream input,
758         ExtensionRegistryLite extensionRegistry,
759         int tag)
760         throws IOException {
761 
762       if (tag == WireFormat.MESSAGE_SET_ITEM_TAG) {
763         mergeMessageSetExtensionFromCodedStream(defaultInstance, input, extensionRegistry);
764         return true;
765       }
766 
767       // TODO(dweis): Do we really want to support non message set wire format in message sets?
768       // Full runtime does... So we do for now.
769       int wireType = WireFormat.getTagWireType(tag);
770       if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) {
771         return parseUnknownField(defaultInstance, input, extensionRegistry, tag);
772       } else {
773         // TODO(dweis): Should we throw on invalid input? Full runtime does not...
774         return input.skipField(tag);
775       }
776     }
777 
778     /**
779      * Merges the message set from the input stream; requires message set wire format.
780      *
781      * @param defaultInstance the default instance of the containing message we are parsing in
782      * @param input the stream to parse from
783      * @param extensionRegistry the registry to use when parsing
784      */
mergeMessageSetExtensionFromCodedStream( MessageType defaultInstance, CodedInputStream input, ExtensionRegistryLite extensionRegistry)785     private <MessageType extends MessageLite> void mergeMessageSetExtensionFromCodedStream(
786         MessageType defaultInstance,
787         CodedInputStream input,
788         ExtensionRegistryLite extensionRegistry)
789         throws IOException {
790       // The wire format for MessageSet is:
791       //   message MessageSet {
792       //     repeated group Item = 1 {
793       //       required int32 typeId = 2;
794       //       required bytes message = 3;
795       //     }
796       //   }
797       // "typeId" is the extension's field number.  The extension can only be
798       // a message type, where "message" contains the encoded bytes of that
799       // message.
800       //
801       // In practice, we will probably never see a MessageSet item in which
802       // the message appears before the type ID, or where either field does not
803       // appear exactly once.  However, in theory such cases are valid, so we
804       // should be prepared to accept them.
805 
806       int typeId = 0;
807       ByteString rawBytes = null; // If we encounter "message" before "typeId"
808       GeneratedExtension<?, ?> extension = null;
809 
810       // Read bytes from input, if we get it's type first then parse it eagerly,
811       // otherwise we store the raw bytes in a local variable.
812       while (true) {
813         final int tag = input.readTag();
814         if (tag == 0) {
815           break;
816         }
817 
818         if (tag == WireFormat.MESSAGE_SET_TYPE_ID_TAG) {
819           typeId = input.readUInt32();
820           if (typeId != 0) {
821             extension = extensionRegistry.findLiteExtensionByNumber(defaultInstance, typeId);
822           }
823 
824         } else if (tag == WireFormat.MESSAGE_SET_MESSAGE_TAG) {
825           if (typeId != 0) {
826             if (extension != null) {
827               // We already know the type, so we can parse directly from the
828               // input with no copying.  Hooray!
829               eagerlyMergeMessageSetExtension(input, extension, extensionRegistry, typeId);
830               rawBytes = null;
831               continue;
832             }
833           }
834           // We haven't seen a type ID yet or we want parse message lazily.
835           rawBytes = input.readBytes();
836 
837         } else { // Unknown tag. Skip it.
838           if (!input.skipField(tag)) {
839             break; // End of group
840           }
841         }
842       }
843       input.checkLastTagWas(WireFormat.MESSAGE_SET_ITEM_END_TAG);
844 
845       // Process the raw bytes.
846       if (rawBytes != null && typeId != 0) { // Zero is not a valid type ID.
847         if (extension != null) { // We known the type
848           mergeMessageSetExtensionFromBytes(rawBytes, extensionRegistry, extension);
849         } else { // We don't know how to parse this. Ignore it.
850           if (rawBytes != null) {
851             mergeLengthDelimitedField(typeId, rawBytes);
852           }
853         }
854       }
855     }
856 
eagerlyMergeMessageSetExtension( CodedInputStream input, GeneratedExtension<?, ?> extension, ExtensionRegistryLite extensionRegistry, int typeId)857     private void eagerlyMergeMessageSetExtension(
858         CodedInputStream input,
859         GeneratedExtension<?, ?> extension,
860         ExtensionRegistryLite extensionRegistry,
861         int typeId)
862         throws IOException {
863       int fieldNumber = typeId;
864       int tag = WireFormat.makeTag(typeId, WireFormat.WIRETYPE_LENGTH_DELIMITED);
865       parseExtension(input, extensionRegistry, extension, tag, fieldNumber);
866     }
867 
mergeMessageSetExtensionFromBytes( ByteString rawBytes, ExtensionRegistryLite extensionRegistry, GeneratedExtension<?, ?> extension)868     private void mergeMessageSetExtensionFromBytes(
869         ByteString rawBytes,
870         ExtensionRegistryLite extensionRegistry,
871         GeneratedExtension<?, ?> extension)
872         throws IOException {
873       MessageLite.Builder subBuilder = null;
874       MessageLite existingValue = (MessageLite) extensions.getField(extension.descriptor);
875       if (existingValue != null) {
876         subBuilder = existingValue.toBuilder();
877       }
878       if (subBuilder == null) {
879         subBuilder = extension.getMessageDefaultInstance().newBuilderForType();
880       }
881       subBuilder.mergeFrom(rawBytes, extensionRegistry);
882       MessageLite value = subBuilder.build();
883 
884       ensureExtensionsAreMutable()
885           .setField(extension.descriptor, extension.singularToFieldSetType(value));
886     }
887 
ensureExtensionsAreMutable()888     FieldSet<ExtensionDescriptor> ensureExtensionsAreMutable() {
889       if (extensions.isImmutable()) {
890         extensions = extensions.clone();
891       }
892       return extensions;
893     }
894 
verifyExtensionContainingType(final GeneratedExtension<MessageType, ?> extension)895     private void verifyExtensionContainingType(final GeneratedExtension<MessageType, ?> extension) {
896       if (extension.getContainingTypeDefaultInstance() != getDefaultInstanceForType()) {
897         // This can only happen if someone uses unchecked operations.
898         throw new IllegalArgumentException(
899             "This extension is for a different message type.  Please make "
900                 + "sure that you are not suppressing any generics type warnings.");
901       }
902     }
903 
904     /** Check if a singular extension is present. */
905     @Override
hasExtension(final ExtensionLite<MessageType, Type> extension)906     public final <Type> boolean hasExtension(final ExtensionLite<MessageType, Type> extension) {
907       GeneratedExtension<MessageType, Type> extensionLite = checkIsLite(extension);
908 
909       verifyExtensionContainingType(extensionLite);
910       return extensions.hasField(extensionLite.descriptor);
911     }
912 
913     /** Get the number of elements in a repeated extension. */
914     @Override
getExtensionCount( final ExtensionLite<MessageType, List<Type>> extension)915     public final <Type> int getExtensionCount(
916         final ExtensionLite<MessageType, List<Type>> extension) {
917       GeneratedExtension<MessageType, List<Type>> extensionLite = checkIsLite(extension);
918 
919       verifyExtensionContainingType(extensionLite);
920       return extensions.getRepeatedFieldCount(extensionLite.descriptor);
921     }
922 
923     /** Get the value of an extension. */
924     @Override
925     @SuppressWarnings("unchecked")
getExtension(final ExtensionLite<MessageType, Type> extension)926     public final <Type> Type getExtension(final ExtensionLite<MessageType, Type> extension) {
927       GeneratedExtension<MessageType, Type> extensionLite = checkIsLite(extension);
928 
929       verifyExtensionContainingType(extensionLite);
930       final Object value = extensions.getField(extensionLite.descriptor);
931       if (value == null) {
932         return extensionLite.defaultValue;
933       } else {
934         return (Type) extensionLite.fromFieldSetType(value);
935       }
936     }
937 
938     /** Get one element of a repeated extension. */
939     @Override
940     @SuppressWarnings("unchecked")
getExtension( final ExtensionLite<MessageType, List<Type>> extension, final int index)941     public final <Type> Type getExtension(
942         final ExtensionLite<MessageType, List<Type>> extension, final int index) {
943       GeneratedExtension<MessageType, List<Type>> extensionLite = checkIsLite(extension);
944 
945       verifyExtensionContainingType(extensionLite);
946       return (Type)
947           extensionLite.singularFromFieldSetType(
948               extensions.getRepeatedField(extensionLite.descriptor, index));
949     }
950 
951     /** Called by subclasses to check if all extensions are initialized. */
extensionsAreInitialized()952     protected boolean extensionsAreInitialized() {
953       return extensions.isInitialized();
954     }
955 
956     /**
957      * Used by subclasses to serialize extensions. Extension ranges may be interleaved with field
958      * numbers, but we must write them in canonical (sorted by field number) order. ExtensionWriter
959      * helps us write individual ranges of extensions at once.
960      */
961     protected class ExtensionWriter {
962       // Imagine how much simpler this code would be if Java iterators had
963       // a way to get the next element without advancing the iterator.
964 
965       private final Iterator<Map.Entry<ExtensionDescriptor, Object>> iter = extensions.iterator();
966       private Map.Entry<ExtensionDescriptor, Object> next;
967       private final boolean messageSetWireFormat;
968 
ExtensionWriter(boolean messageSetWireFormat)969       private ExtensionWriter(boolean messageSetWireFormat) {
970         if (iter.hasNext()) {
971           next = iter.next();
972         }
973         this.messageSetWireFormat = messageSetWireFormat;
974       }
975 
writeUntil(final int end, final CodedOutputStream output)976       public void writeUntil(final int end, final CodedOutputStream output) throws IOException {
977         while (next != null && next.getKey().getNumber() < end) {
978           ExtensionDescriptor extension = next.getKey();
979           if (messageSetWireFormat
980               && extension.getLiteJavaType() == WireFormat.JavaType.MESSAGE
981               && !extension.isRepeated()) {
982             output.writeMessageSetExtension(extension.getNumber(), (MessageLite) next.getValue());
983           } else {
984             FieldSet.writeField(extension, next.getValue(), output);
985           }
986           if (iter.hasNext()) {
987             next = iter.next();
988           } else {
989             next = null;
990           }
991         }
992       }
993     }
994 
newExtensionWriter()995     protected ExtensionWriter newExtensionWriter() {
996       return new ExtensionWriter(false);
997     }
998 
newMessageSetExtensionWriter()999     protected ExtensionWriter newMessageSetExtensionWriter() {
1000       return new ExtensionWriter(true);
1001     }
1002 
1003     /** Called by subclasses to compute the size of extensions. */
extensionsSerializedSize()1004     protected int extensionsSerializedSize() {
1005       return extensions.getSerializedSize();
1006     }
1007 
extensionsSerializedSizeAsMessageSet()1008     protected int extensionsSerializedSizeAsMessageSet() {
1009       return extensions.getMessageSetSerializedSize();
1010     }
1011   }
1012 
1013   /** Lite equivalent of {@link GeneratedMessage.ExtendableBuilder}. */
1014   @SuppressWarnings("unchecked")
1015   public abstract static class ExtendableBuilder<
1016           MessageType extends ExtendableMessage<MessageType, BuilderType>,
1017           BuilderType extends ExtendableBuilder<MessageType, BuilderType>>
1018       extends Builder<MessageType, BuilderType>
1019       implements ExtendableMessageOrBuilder<MessageType, BuilderType> {
ExtendableBuilder(MessageType defaultInstance)1020     protected ExtendableBuilder(MessageType defaultInstance) {
1021       super(defaultInstance);
1022     }
1023 
1024     // For immutable message conversion.
internalSetExtensionSet(FieldSet<ExtensionDescriptor> extensions)1025     void internalSetExtensionSet(FieldSet<ExtensionDescriptor> extensions) {
1026       copyOnWrite();
1027       instance.extensions = extensions;
1028     }
1029 
1030     @Override
copyOnWriteInternal()1031     protected void copyOnWriteInternal() {
1032       super.copyOnWriteInternal();
1033       if (instance.extensions != FieldSet.emptySet()) {
1034         instance.extensions = instance.extensions.clone();
1035       }
1036     }
1037 
ensureExtensionsAreMutable()1038     private FieldSet<ExtensionDescriptor> ensureExtensionsAreMutable() {
1039       FieldSet<ExtensionDescriptor> extensions = instance.extensions;
1040       if (extensions.isImmutable()) {
1041         extensions = extensions.clone();
1042         instance.extensions = extensions;
1043       }
1044       return extensions;
1045     }
1046 
1047     @Override
buildPartial()1048     public final MessageType buildPartial() {
1049       if (!instance.isMutable()) {
1050         return instance;
1051       }
1052 
1053       instance.extensions.makeImmutable();
1054       return super.buildPartial();
1055     }
1056 
verifyExtensionContainingType(final GeneratedExtension<MessageType, ?> extension)1057     private void verifyExtensionContainingType(final GeneratedExtension<MessageType, ?> extension) {
1058       if (extension.getContainingTypeDefaultInstance() != getDefaultInstanceForType()) {
1059         // This can only happen if someone uses unchecked operations.
1060         throw new IllegalArgumentException(
1061             "This extension is for a different message type.  Please make "
1062                 + "sure that you are not suppressing any generics type warnings.");
1063       }
1064     }
1065 
1066     /** Check if a singular extension is present. */
1067     @Override
hasExtension(final ExtensionLite<MessageType, Type> extension)1068     public final <Type> boolean hasExtension(final ExtensionLite<MessageType, Type> extension) {
1069       return instance.hasExtension(extension);
1070     }
1071 
1072     /** Get the number of elements in a repeated extension. */
1073     @Override
getExtensionCount( final ExtensionLite<MessageType, List<Type>> extension)1074     public final <Type> int getExtensionCount(
1075         final ExtensionLite<MessageType, List<Type>> extension) {
1076       return instance.getExtensionCount(extension);
1077     }
1078 
1079     /** Get the value of an extension. */
1080     @Override
1081     @SuppressWarnings("unchecked")
getExtension(final ExtensionLite<MessageType, Type> extension)1082     public final <Type> Type getExtension(final ExtensionLite<MessageType, Type> extension) {
1083       return instance.getExtension(extension);
1084     }
1085 
1086     /** Get one element of a repeated extension. */
1087     @Override
1088     @SuppressWarnings("unchecked")
getExtension( final ExtensionLite<MessageType, List<Type>> extension, final int index)1089     public final <Type> Type getExtension(
1090         final ExtensionLite<MessageType, List<Type>> extension, final int index) {
1091       return instance.getExtension(extension, index);
1092     }
1093 
1094     /** Set the value of an extension. */
setExtension( final ExtensionLite<MessageType, Type> extension, final Type value)1095     public final <Type> BuilderType setExtension(
1096         final ExtensionLite<MessageType, Type> extension, final Type value) {
1097       GeneratedExtension<MessageType, Type> extensionLite = checkIsLite(extension);
1098 
1099       verifyExtensionContainingType(extensionLite);
1100       copyOnWrite();
1101       ensureExtensionsAreMutable()
1102           .setField(extensionLite.descriptor, extensionLite.toFieldSetType(value));
1103       return (BuilderType) this;
1104     }
1105 
1106     /** Set the value of one element of a repeated extension. */
setExtension( final ExtensionLite<MessageType, List<Type>> extension, final int index, final Type value)1107     public final <Type> BuilderType setExtension(
1108         final ExtensionLite<MessageType, List<Type>> extension, final int index, final Type value) {
1109       GeneratedExtension<MessageType, List<Type>> extensionLite = checkIsLite(extension);
1110 
1111       verifyExtensionContainingType(extensionLite);
1112       copyOnWrite();
1113       ensureExtensionsAreMutable()
1114           .setRepeatedField(
1115               extensionLite.descriptor, index, extensionLite.singularToFieldSetType(value));
1116       return (BuilderType) this;
1117     }
1118 
1119     /** Append a value to a repeated extension. */
addExtension( final ExtensionLite<MessageType, List<Type>> extension, final Type value)1120     public final <Type> BuilderType addExtension(
1121         final ExtensionLite<MessageType, List<Type>> extension, final Type value) {
1122       GeneratedExtension<MessageType, List<Type>> extensionLite = checkIsLite(extension);
1123 
1124       verifyExtensionContainingType(extensionLite);
1125       copyOnWrite();
1126       ensureExtensionsAreMutable()
1127           .addRepeatedField(extensionLite.descriptor, extensionLite.singularToFieldSetType(value));
1128       return (BuilderType) this;
1129     }
1130 
1131     /** Clear an extension. */
clearExtension(final ExtensionLite<MessageType, ?> extension)1132     public final BuilderType clearExtension(final ExtensionLite<MessageType, ?> extension) {
1133       GeneratedExtension<MessageType, ?> extensionLite = checkIsLite(extension);
1134 
1135       verifyExtensionContainingType(extensionLite);
1136       copyOnWrite();
1137       ensureExtensionsAreMutable().clearField(extensionLite.descriptor);
1138       return (BuilderType) this;
1139     }
1140   }
1141 
1142   // -----------------------------------------------------------------
1143 
1144   /** For use by generated code only. */
1145   public static <ContainingType extends MessageLite, Type>
newSingularGeneratedExtension( final ContainingType containingTypeDefaultInstance, final Type defaultValue, final MessageLite messageDefaultInstance, final Internal.EnumLiteMap<?> enumTypeMap, final int number, final WireFormat.FieldType type, final Class singularType)1146       GeneratedExtension<ContainingType, Type> newSingularGeneratedExtension(
1147           final ContainingType containingTypeDefaultInstance,
1148           final Type defaultValue,
1149           final MessageLite messageDefaultInstance,
1150           final Internal.EnumLiteMap<?> enumTypeMap,
1151           final int number,
1152           final WireFormat.FieldType type,
1153           final Class singularType) {
1154     return new GeneratedExtension<ContainingType, Type>(
1155         containingTypeDefaultInstance,
1156         defaultValue,
1157         messageDefaultInstance,
1158         new ExtensionDescriptor(
1159             enumTypeMap, number, type, /* isRepeated= */ false, /* isPacked= */ false),
1160         singularType);
1161   }
1162 
1163   /** For use by generated code only. */
1164   public static <ContainingType extends MessageLite, Type>
newRepeatedGeneratedExtension( final ContainingType containingTypeDefaultInstance, final MessageLite messageDefaultInstance, final Internal.EnumLiteMap<?> enumTypeMap, final int number, final WireFormat.FieldType type, final boolean isPacked, final Class singularType)1165       GeneratedExtension<ContainingType, Type> newRepeatedGeneratedExtension(
1166           final ContainingType containingTypeDefaultInstance,
1167           final MessageLite messageDefaultInstance,
1168           final Internal.EnumLiteMap<?> enumTypeMap,
1169           final int number,
1170           final WireFormat.FieldType type,
1171           final boolean isPacked,
1172           final Class singularType) {
1173     @SuppressWarnings("unchecked") // Subclasses ensure Type is a List
1174     Type emptyList = (Type) Collections.emptyList();
1175     return new GeneratedExtension<ContainingType, Type>(
1176         containingTypeDefaultInstance,
1177         emptyList,
1178         messageDefaultInstance,
1179         new ExtensionDescriptor(enumTypeMap, number, type, /* isRepeated= */ true, isPacked),
1180         singularType);
1181   }
1182 
1183   static final class ExtensionDescriptor
1184       implements FieldSet.FieldDescriptorLite<ExtensionDescriptor> {
ExtensionDescriptor( final Internal.EnumLiteMap<?> enumTypeMap, final int number, final WireFormat.FieldType type, final boolean isRepeated, final boolean isPacked)1185     ExtensionDescriptor(
1186         final Internal.EnumLiteMap<?> enumTypeMap,
1187         final int number,
1188         final WireFormat.FieldType type,
1189         final boolean isRepeated,
1190         final boolean isPacked) {
1191       this.enumTypeMap = enumTypeMap;
1192       this.number = number;
1193       this.type = type;
1194       this.isRepeated = isRepeated;
1195       this.isPacked = isPacked;
1196     }
1197 
1198     final Internal.EnumLiteMap<?> enumTypeMap;
1199     final int number;
1200     final WireFormat.FieldType type;
1201     final boolean isRepeated;
1202     final boolean isPacked;
1203 
1204     @Override
getNumber()1205     public int getNumber() {
1206       return number;
1207     }
1208 
1209     @Override
getLiteType()1210     public WireFormat.FieldType getLiteType() {
1211       return type;
1212     }
1213 
1214     @Override
getLiteJavaType()1215     public WireFormat.JavaType getLiteJavaType() {
1216       return type.getJavaType();
1217     }
1218 
1219     @Override
isRepeated()1220     public boolean isRepeated() {
1221       return isRepeated;
1222     }
1223 
1224     @Override
isPacked()1225     public boolean isPacked() {
1226       return isPacked;
1227     }
1228 
1229     @Override
getEnumType()1230     public Internal.EnumLiteMap<?> getEnumType() {
1231       return enumTypeMap;
1232     }
1233 
1234     @Override
1235     @SuppressWarnings("unchecked")
internalMergeFrom(MessageLite.Builder to, MessageLite from)1236     public MessageLite.Builder internalMergeFrom(MessageLite.Builder to, MessageLite from) {
1237       return ((Builder) to).mergeFrom((GeneratedMessageLite) from);
1238     }
1239 
1240 
1241     @Override
compareTo(ExtensionDescriptor other)1242     public int compareTo(ExtensionDescriptor other) {
1243       return number - other.number;
1244     }
1245   }
1246 
1247   // =================================================================
1248 
1249   /** Calls Class.getMethod and throws a RuntimeException if it fails. */
1250   @SuppressWarnings("unchecked")
getMethodOrDie(Class clazz, String name, Class... params)1251   static Method getMethodOrDie(Class clazz, String name, Class... params) {
1252     try {
1253       return clazz.getMethod(name, params);
1254     } catch (NoSuchMethodException e) {
1255       throw new RuntimeException(
1256           "Generated message class \"" + clazz.getName() + "\" missing method \"" + name + "\".",
1257           e);
1258     }
1259   }
1260 
1261   /** Calls invoke and throws a RuntimeException if it fails. */
invokeOrDie(Method method, Object object, Object... params)1262   static Object invokeOrDie(Method method, Object object, Object... params) {
1263     try {
1264       return method.invoke(object, params);
1265     } catch (IllegalAccessException e) {
1266       throw new RuntimeException(
1267           "Couldn't use Java reflection to implement protocol message reflection.", e);
1268     } catch (InvocationTargetException e) {
1269       final Throwable cause = e.getCause();
1270       if (cause instanceof RuntimeException) {
1271         throw (RuntimeException) cause;
1272       } else if (cause instanceof Error) {
1273         throw (Error) cause;
1274       } else {
1275         throw new RuntimeException(
1276             "Unexpected exception thrown by generated accessor method.", cause);
1277       }
1278     }
1279   }
1280 
1281 
1282   /**
1283    * Lite equivalent to {@link GeneratedMessage.GeneratedExtension}.
1284    *
1285    * <p>Users should ignore the contents of this class and only use objects of this type as
1286    * parameters to extension accessors and ExtensionRegistry.add().
1287    */
1288   public static class GeneratedExtension<ContainingType extends MessageLite, Type>
1289       extends ExtensionLite<ContainingType, Type> {
1290 
1291     /**
1292      * Create a new instance with the given parameters.
1293      *
1294      * <p>The last parameter {@code singularType} is only needed for enum types. We store integer
1295      * values for enum types in a {@link ExtendableMessage} and use Java reflection to convert an
1296      * integer value back into a concrete enum object.
1297      */
GeneratedExtension( final ContainingType containingTypeDefaultInstance, final Type defaultValue, final MessageLite messageDefaultInstance, final ExtensionDescriptor descriptor, final Class singularType)1298     GeneratedExtension(
1299         final ContainingType containingTypeDefaultInstance,
1300         final Type defaultValue,
1301         final MessageLite messageDefaultInstance,
1302         final ExtensionDescriptor descriptor,
1303         final Class singularType) {
1304       // Defensive checks to verify the correct initialization order of
1305       // GeneratedExtensions and their related GeneratedMessages.
1306       if (containingTypeDefaultInstance == null) {
1307         throw new IllegalArgumentException("Null containingTypeDefaultInstance");
1308       }
1309       if (descriptor.getLiteType() == WireFormat.FieldType.MESSAGE
1310           && messageDefaultInstance == null) {
1311         throw new IllegalArgumentException("Null messageDefaultInstance");
1312       }
1313       this.containingTypeDefaultInstance = containingTypeDefaultInstance;
1314       this.defaultValue = defaultValue;
1315       this.messageDefaultInstance = messageDefaultInstance;
1316       this.descriptor = descriptor;
1317     }
1318 
1319     final ContainingType containingTypeDefaultInstance;
1320     final Type defaultValue;
1321     final MessageLite messageDefaultInstance;
1322     final ExtensionDescriptor descriptor;
1323 
1324     /** Default instance of the type being extended, used to identify that type. */
getContainingTypeDefaultInstance()1325     public ContainingType getContainingTypeDefaultInstance() {
1326       return containingTypeDefaultInstance;
1327     }
1328 
1329     /** Get the field number. */
1330     @Override
getNumber()1331     public int getNumber() {
1332       return descriptor.getNumber();
1333     }
1334 
1335     /**
1336      * If the extension is an embedded message or group, returns the default instance of the
1337      * message.
1338      */
1339     @Override
getMessageDefaultInstance()1340     public MessageLite getMessageDefaultInstance() {
1341       return messageDefaultInstance;
1342     }
1343 
1344     @SuppressWarnings("unchecked")
fromFieldSetType(final Object value)1345     Object fromFieldSetType(final Object value) {
1346       if (descriptor.isRepeated()) {
1347         if (descriptor.getLiteJavaType() == WireFormat.JavaType.ENUM) {
1348           final List result = new ArrayList<>();
1349           for (final Object element : (List) value) {
1350             result.add(singularFromFieldSetType(element));
1351           }
1352           return result;
1353         } else {
1354           return value;
1355         }
1356       } else {
1357         return singularFromFieldSetType(value);
1358       }
1359     }
1360 
singularFromFieldSetType(final Object value)1361     Object singularFromFieldSetType(final Object value) {
1362       if (descriptor.getLiteJavaType() == WireFormat.JavaType.ENUM) {
1363         return descriptor.enumTypeMap.findValueByNumber((Integer) value);
1364       } else {
1365         return value;
1366       }
1367     }
1368 
1369     @SuppressWarnings("unchecked")
toFieldSetType(final Object value)1370     Object toFieldSetType(final Object value) {
1371       if (descriptor.isRepeated()) {
1372         if (descriptor.getLiteJavaType() == WireFormat.JavaType.ENUM) {
1373           final List result = new ArrayList<>();
1374           for (final Object element : (List) value) {
1375             result.add(singularToFieldSetType(element));
1376           }
1377           return result;
1378         } else {
1379           return value;
1380         }
1381       } else {
1382         return singularToFieldSetType(value);
1383       }
1384     }
1385 
singularToFieldSetType(final Object value)1386     Object singularToFieldSetType(final Object value) {
1387       if (descriptor.getLiteJavaType() == WireFormat.JavaType.ENUM) {
1388         return ((Internal.EnumLite) value).getNumber();
1389       } else {
1390         return value;
1391       }
1392     }
1393 
1394     @Override
getLiteType()1395     public FieldType getLiteType() {
1396       return descriptor.getLiteType();
1397     }
1398 
1399     @Override
isRepeated()1400     public boolean isRepeated() {
1401       return descriptor.isRepeated;
1402     }
1403 
1404     @Override
getDefaultValue()1405     public Type getDefaultValue() {
1406       return defaultValue;
1407     }
1408   }
1409 
1410   /**
1411    * A serialized (serializable) form of the generated message. Stores the message as a class name
1412    * and a byte array.
1413    */
1414   protected static final class SerializedForm implements Serializable {
1415 
of(MessageLite message)1416     public static SerializedForm of(MessageLite message) {
1417       return new SerializedForm(message);
1418     }
1419 
1420     private static final long serialVersionUID = 0L;
1421 
1422     // since v3.6.1
1423     private final Class<?> messageClass;
1424     // only included for backwards compatibility before messageClass was added
1425     private final String messageClassName;
1426     private final byte[] asBytes;
1427 
1428     /**
1429      * Creates the serialized form by calling {@link com.google.protobuf.MessageLite#toByteArray}.
1430      *
1431      * @param regularForm the message to serialize
1432      */
SerializedForm(MessageLite regularForm)1433     SerializedForm(MessageLite regularForm) {
1434       messageClass = regularForm.getClass();
1435       messageClassName = messageClass.getName();
1436       asBytes = regularForm.toByteArray();
1437     }
1438 
1439     /**
1440      * When read from an ObjectInputStream, this method converts this object back to the regular
1441      * form. Part of Java's serialization magic.
1442      *
1443      * @return a GeneratedMessage of the type that was serialized
1444      */
1445     @SuppressWarnings("unchecked")
readResolve()1446     protected Object readResolve() throws ObjectStreamException {
1447       try {
1448         Class<?> messageClass = resolveMessageClass();
1449         java.lang.reflect.Field defaultInstanceField =
1450             messageClass.getDeclaredField("DEFAULT_INSTANCE");
1451         defaultInstanceField.setAccessible(true);
1452         MessageLite defaultInstance = (MessageLite) defaultInstanceField.get(null);
1453         return defaultInstance.newBuilderForType().mergeFrom(asBytes).buildPartial();
1454       } catch (ClassNotFoundException e) {
1455         throw new RuntimeException("Unable to find proto buffer class: " + messageClassName, e);
1456       } catch (NoSuchFieldException e) {
1457         return readResolveFallback();
1458       } catch (SecurityException e) {
1459         throw new RuntimeException("Unable to call DEFAULT_INSTANCE in " + messageClassName, e);
1460       } catch (IllegalAccessException e) {
1461         throw new RuntimeException("Unable to call parsePartialFrom", e);
1462       } catch (InvalidProtocolBufferException e) {
1463         throw new RuntimeException("Unable to understand proto buffer", e);
1464       }
1465     }
1466 
1467     /**
1468      * @deprecated from v3.0.0-beta-3+, for compatibility with v2.5.0 and v2.6.1 generated code.
1469      */
1470     @Deprecated
readResolveFallback()1471     private Object readResolveFallback() throws ObjectStreamException {
1472       try {
1473         Class<?> messageClass = resolveMessageClass();
1474         java.lang.reflect.Field defaultInstanceField =
1475             messageClass.getDeclaredField("defaultInstance");
1476         defaultInstanceField.setAccessible(true);
1477         MessageLite defaultInstance = (MessageLite) defaultInstanceField.get(null);
1478         return defaultInstance.newBuilderForType()
1479             .mergeFrom(asBytes)
1480             .buildPartial();
1481       } catch (ClassNotFoundException e) {
1482         throw new RuntimeException("Unable to find proto buffer class: " + messageClassName, e);
1483       } catch (NoSuchFieldException e) {
1484         throw new RuntimeException("Unable to find defaultInstance in " + messageClassName, e);
1485       } catch (SecurityException e) {
1486         throw new RuntimeException("Unable to call defaultInstance in " + messageClassName, e);
1487       } catch (IllegalAccessException e) {
1488         throw new RuntimeException("Unable to call parsePartialFrom", e);
1489       } catch (InvalidProtocolBufferException e) {
1490         throw new RuntimeException("Unable to understand proto buffer", e);
1491       }
1492     }
1493 
resolveMessageClass()1494     private Class<?> resolveMessageClass() throws ClassNotFoundException {
1495       return messageClass != null ? messageClass : Class.forName(messageClassName);
1496     }
1497   }
1498 
1499   /** Checks that the {@link Extension} is Lite and returns it as a {@link GeneratedExtension}. */
1500   private static <
1501           MessageType extends ExtendableMessage<MessageType, BuilderType>,
1502           BuilderType extends ExtendableBuilder<MessageType, BuilderType>,
1503           T>
checkIsLite(ExtensionLite<MessageType, T> extension)1504       GeneratedExtension<MessageType, T> checkIsLite(ExtensionLite<MessageType, T> extension) {
1505     if (!extension.isLite()) {
1506       throw new IllegalArgumentException("Expected a lite extension.");
1507     }
1508 
1509     return (GeneratedExtension<MessageType, T>) extension;
1510   }
1511 
1512   /**
1513    * A static helper method for checking if a message is initialized, optionally memoizing.
1514    *
1515    * <p>For use by generated code only.
1516    */
isInitialized( T message, boolean shouldMemoize)1517   protected static final <T extends GeneratedMessageLite<T, ?>> boolean isInitialized(
1518       T message, boolean shouldMemoize) {
1519     byte memoizedIsInitialized =
1520         (Byte) message.dynamicMethod(MethodToInvoke.GET_MEMOIZED_IS_INITIALIZED);
1521     if (memoizedIsInitialized == 1) {
1522       return true;
1523     }
1524     if (memoizedIsInitialized == 0) {
1525       return false;
1526     }
1527     boolean isInitialized = Protobuf.getInstance().schemaFor(message).isInitialized(message);
1528     if (shouldMemoize) {
1529       message.dynamicMethod(
1530           MethodToInvoke.SET_MEMOIZED_IS_INITIALIZED, isInitialized ? message : null);
1531     }
1532     return isInitialized;
1533   }
1534 
emptyIntList()1535   protected static IntList emptyIntList() {
1536     return IntArrayList.emptyList();
1537   }
1538 
mutableCopy(IntList list)1539   protected static IntList mutableCopy(IntList list) {
1540     int size = list.size();
1541     return list.mutableCopyWithCapacity(
1542         size == 0 ? AbstractProtobufList.DEFAULT_CAPACITY : size * 2);
1543   }
1544 
emptyLongList()1545   protected static LongList emptyLongList() {
1546     return LongArrayList.emptyList();
1547   }
1548 
mutableCopy(LongList list)1549   protected static LongList mutableCopy(LongList list) {
1550     int size = list.size();
1551     return list.mutableCopyWithCapacity(
1552         size == 0 ? AbstractProtobufList.DEFAULT_CAPACITY : size * 2);
1553   }
1554 
emptyFloatList()1555   protected static FloatList emptyFloatList() {
1556     return FloatArrayList.emptyList();
1557   }
1558 
mutableCopy(FloatList list)1559   protected static FloatList mutableCopy(FloatList list) {
1560     int size = list.size();
1561     return list.mutableCopyWithCapacity(
1562         size == 0 ? AbstractProtobufList.DEFAULT_CAPACITY : size * 2);
1563   }
1564 
emptyDoubleList()1565   protected static DoubleList emptyDoubleList() {
1566     return DoubleArrayList.emptyList();
1567   }
1568 
mutableCopy(DoubleList list)1569   protected static DoubleList mutableCopy(DoubleList list) {
1570     int size = list.size();
1571     return list.mutableCopyWithCapacity(
1572         size == 0 ? AbstractProtobufList.DEFAULT_CAPACITY : size * 2);
1573   }
1574 
emptyBooleanList()1575   protected static BooleanList emptyBooleanList() {
1576     return BooleanArrayList.emptyList();
1577   }
1578 
mutableCopy(BooleanList list)1579   protected static BooleanList mutableCopy(BooleanList list) {
1580     int size = list.size();
1581     return list.mutableCopyWithCapacity(
1582         size == 0 ? AbstractProtobufList.DEFAULT_CAPACITY : size * 2);
1583   }
1584 
emptyProtobufList()1585   protected static <E> ProtobufList<E> emptyProtobufList() {
1586     return ProtobufArrayList.emptyList();
1587   }
1588 
mutableCopy(ProtobufList<E> list)1589   protected static <E> ProtobufList<E> mutableCopy(ProtobufList<E> list) {
1590     int size = list.size();
1591     return list.mutableCopyWithCapacity(
1592         size == 0 ? AbstractProtobufList.DEFAULT_CAPACITY : size * 2);
1593   }
1594 
1595   /**
1596    * A {@link Parser} implementation that delegates to the default instance.
1597    *
1598    * <p>For use by generated code only.
1599    */
1600   protected static class DefaultInstanceBasedParser<T extends GeneratedMessageLite<T, ?>>
1601       extends AbstractParser<T> {
1602 
1603     private final T defaultInstance;
1604 
DefaultInstanceBasedParser(T defaultInstance)1605     public DefaultInstanceBasedParser(T defaultInstance) {
1606       this.defaultInstance = defaultInstance;
1607     }
1608 
1609     @Override
parsePartialFrom(CodedInputStream input, ExtensionRegistryLite extensionRegistry)1610     public T parsePartialFrom(CodedInputStream input, ExtensionRegistryLite extensionRegistry)
1611         throws InvalidProtocolBufferException {
1612       return GeneratedMessageLite.parsePartialFrom(defaultInstance, input, extensionRegistry);
1613     }
1614 
1615     @Override
parsePartialFrom( byte[] input, int offset, int length, ExtensionRegistryLite extensionRegistry)1616     public T parsePartialFrom(
1617         byte[] input, int offset, int length, ExtensionRegistryLite extensionRegistry)
1618         throws InvalidProtocolBufferException {
1619       return GeneratedMessageLite.parsePartialFrom(
1620           defaultInstance, input, offset, length, extensionRegistry);
1621     }
1622   }
1623 
1624   /**
1625    * A static helper method for parsing a partial from input using the extension registry and the
1626    * instance.
1627    */
1628   // TODO(dweis): Should this verify that the last tag was 0?
parsePartialFrom( T instance, CodedInputStream input, ExtensionRegistryLite extensionRegistry)1629   static <T extends GeneratedMessageLite<T, ?>> T parsePartialFrom(
1630       T instance, CodedInputStream input, ExtensionRegistryLite extensionRegistry)
1631       throws InvalidProtocolBufferException {
1632     @SuppressWarnings("unchecked") // Guaranteed by protoc
1633     T result = instance.newMutableInstance();
1634     try {
1635       // TODO(yilunchong): Try to make input with type CodedInpuStream.ArrayDecoder use
1636       // fast path.
1637       Schema<T> schema = Protobuf.getInstance().schemaFor(result);
1638       schema.mergeFrom(result, CodedInputStreamReader.forCodedInput(input), extensionRegistry);
1639       schema.makeImmutable(result);
1640     } catch (IOException e) {
1641       if (e.getCause() instanceof InvalidProtocolBufferException) {
1642         throw (InvalidProtocolBufferException) e.getCause();
1643       }
1644       throw new InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(result);
1645     } catch (RuntimeException e) {
1646       if (e.getCause() instanceof InvalidProtocolBufferException) {
1647         throw (InvalidProtocolBufferException) e.getCause();
1648       }
1649       throw e;
1650     }
1651     return result;
1652   }
1653 
1654   /** A static helper method for parsing a partial from byte array. */
parsePartialFrom( T instance, byte[] input, int offset, int length, ExtensionRegistryLite extensionRegistry)1655   static <T extends GeneratedMessageLite<T, ?>> T parsePartialFrom(
1656       T instance, byte[] input, int offset, int length, ExtensionRegistryLite extensionRegistry)
1657       throws InvalidProtocolBufferException {
1658     @SuppressWarnings("unchecked") // Guaranteed by protoc
1659     T result = instance.newMutableInstance();
1660     try {
1661       Schema<T> schema = Protobuf.getInstance().schemaFor(result);
1662       schema.mergeFrom(
1663           result, input, offset, offset + length, new ArrayDecoders.Registers(extensionRegistry));
1664       schema.makeImmutable(result);
1665     } catch (IOException e) {
1666       if (e.getCause() instanceof InvalidProtocolBufferException) {
1667         throw (InvalidProtocolBufferException) e.getCause();
1668       }
1669       throw new InvalidProtocolBufferException(e.getMessage()).setUnfinishedMessage(result);
1670     } catch (IndexOutOfBoundsException e) {
1671       throw InvalidProtocolBufferException.truncatedMessage().setUnfinishedMessage(result);
1672     }
1673     return result;
1674   }
1675 
parsePartialFrom( T defaultInstance, CodedInputStream input)1676   protected static <T extends GeneratedMessageLite<T, ?>> T parsePartialFrom(
1677       T defaultInstance, CodedInputStream input) throws InvalidProtocolBufferException {
1678     return parsePartialFrom(defaultInstance, input, ExtensionRegistryLite.getEmptyRegistry());
1679   }
1680 
1681   /**
1682    * Helper method to check if message is initialized.
1683    *
1684    * @throws InvalidProtocolBufferException if it is not initialized.
1685    * @return The message to check.
1686    */
checkMessageInitialized(T message)1687   private static <T extends GeneratedMessageLite<T, ?>> T checkMessageInitialized(T message)
1688       throws InvalidProtocolBufferException {
1689     if (message != null && !message.isInitialized()) {
1690       throw message
1691           .newUninitializedMessageException()
1692           .asInvalidProtocolBufferException()
1693           .setUnfinishedMessage(message);
1694     }
1695     return message;
1696   }
1697 
1698   // Validates last tag.
parseFrom( T defaultInstance, ByteBuffer data, ExtensionRegistryLite extensionRegistry)1699   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1700       T defaultInstance, ByteBuffer data, ExtensionRegistryLite extensionRegistry)
1701       throws InvalidProtocolBufferException {
1702     return checkMessageInitialized(
1703         parseFrom(defaultInstance, CodedInputStream.newInstance(data), extensionRegistry));
1704   }
1705 
1706   // Validates last tag.
parseFrom( T defaultInstance, ByteBuffer data)1707   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1708       T defaultInstance, ByteBuffer data) throws InvalidProtocolBufferException {
1709     return parseFrom(defaultInstance, data, ExtensionRegistryLite.getEmptyRegistry());
1710   }
1711 
1712   // Validates last tag.
parseFrom( T defaultInstance, ByteString data)1713   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1714       T defaultInstance, ByteString data) throws InvalidProtocolBufferException {
1715     return checkMessageInitialized(
1716         parseFrom(defaultInstance, data, ExtensionRegistryLite.getEmptyRegistry()));
1717   }
1718 
1719   // Validates last tag.
parseFrom( T defaultInstance, ByteString data, ExtensionRegistryLite extensionRegistry)1720   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1721       T defaultInstance, ByteString data, ExtensionRegistryLite extensionRegistry)
1722       throws InvalidProtocolBufferException {
1723     return checkMessageInitialized(parsePartialFrom(defaultInstance, data, extensionRegistry));
1724   }
1725 
1726   // This is a special case since we want to verify that the last tag is 0. We assume we exhaust the
1727   // ByteString.
parsePartialFrom( T defaultInstance, ByteString data, ExtensionRegistryLite extensionRegistry)1728   private static <T extends GeneratedMessageLite<T, ?>> T parsePartialFrom(
1729       T defaultInstance, ByteString data, ExtensionRegistryLite extensionRegistry)
1730       throws InvalidProtocolBufferException {
1731     T message;
1732     try {
1733       CodedInputStream input = data.newCodedInput();
1734       message = parsePartialFrom(defaultInstance, input, extensionRegistry);
1735       try {
1736         input.checkLastTagWas(0);
1737       } catch (InvalidProtocolBufferException e) {
1738         throw e.setUnfinishedMessage(message);
1739       }
1740       return message;
1741     } catch (InvalidProtocolBufferException e) {
1742       throw e;
1743     }
1744   }
1745 
1746   // This is a special case since we want to verify that the last tag is 0. We assume we exhaust the
1747   // ByteString.
parsePartialFrom( T defaultInstance, byte[] data, ExtensionRegistryLite extensionRegistry)1748   private static <T extends GeneratedMessageLite<T, ?>> T parsePartialFrom(
1749       T defaultInstance, byte[] data, ExtensionRegistryLite extensionRegistry)
1750       throws InvalidProtocolBufferException {
1751     return checkMessageInitialized(
1752         parsePartialFrom(defaultInstance, data, 0, data.length, extensionRegistry));
1753   }
1754 
1755   // Validates last tag.
parseFrom( T defaultInstance, byte[] data)1756   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1757       T defaultInstance, byte[] data) throws InvalidProtocolBufferException {
1758     return checkMessageInitialized(parsePartialFrom(
1759         defaultInstance, data, 0, data.length, ExtensionRegistryLite.getEmptyRegistry()));
1760   }
1761 
1762   // Validates last tag.
parseFrom( T defaultInstance, byte[] data, ExtensionRegistryLite extensionRegistry)1763   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1764       T defaultInstance, byte[] data, ExtensionRegistryLite extensionRegistry)
1765       throws InvalidProtocolBufferException {
1766     return checkMessageInitialized(
1767         parsePartialFrom(defaultInstance, data, 0, data.length, extensionRegistry));
1768   }
1769 
1770   // Does not validate last tag.
parseFrom( T defaultInstance, InputStream input)1771   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1772       T defaultInstance, InputStream input) throws InvalidProtocolBufferException {
1773     return checkMessageInitialized(
1774         parsePartialFrom(
1775             defaultInstance,
1776             CodedInputStream.newInstance(input),
1777             ExtensionRegistryLite.getEmptyRegistry()));
1778   }
1779 
1780   // Does not validate last tag.
parseFrom( T defaultInstance, InputStream input, ExtensionRegistryLite extensionRegistry)1781   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1782       T defaultInstance, InputStream input, ExtensionRegistryLite extensionRegistry)
1783       throws InvalidProtocolBufferException {
1784     return checkMessageInitialized(
1785         parsePartialFrom(defaultInstance, CodedInputStream.newInstance(input), extensionRegistry));
1786   }
1787 
1788   // Does not validate last tag.
parseFrom( T defaultInstance, CodedInputStream input)1789   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1790       T defaultInstance, CodedInputStream input) throws InvalidProtocolBufferException {
1791     return parseFrom(defaultInstance, input, ExtensionRegistryLite.getEmptyRegistry());
1792   }
1793 
1794   // Does not validate last tag.
parseFrom( T defaultInstance, CodedInputStream input, ExtensionRegistryLite extensionRegistry)1795   protected static <T extends GeneratedMessageLite<T, ?>> T parseFrom(
1796       T defaultInstance, CodedInputStream input, ExtensionRegistryLite extensionRegistry)
1797       throws InvalidProtocolBufferException {
1798     return checkMessageInitialized(parsePartialFrom(defaultInstance, input, extensionRegistry));
1799   }
1800 
1801   // Validates last tag.
parseDelimitedFrom( T defaultInstance, InputStream input)1802   protected static <T extends GeneratedMessageLite<T, ?>> T parseDelimitedFrom(
1803       T defaultInstance, InputStream input) throws InvalidProtocolBufferException {
1804     return checkMessageInitialized(
1805         parsePartialDelimitedFrom(
1806             defaultInstance, input, ExtensionRegistryLite.getEmptyRegistry()));
1807   }
1808 
1809   // Validates last tag.
parseDelimitedFrom( T defaultInstance, InputStream input, ExtensionRegistryLite extensionRegistry)1810   protected static <T extends GeneratedMessageLite<T, ?>> T parseDelimitedFrom(
1811       T defaultInstance, InputStream input, ExtensionRegistryLite extensionRegistry)
1812       throws InvalidProtocolBufferException {
1813     return checkMessageInitialized(
1814         parsePartialDelimitedFrom(defaultInstance, input, extensionRegistry));
1815   }
1816 
parsePartialDelimitedFrom( T defaultInstance, InputStream input, ExtensionRegistryLite extensionRegistry)1817   private static <T extends GeneratedMessageLite<T, ?>> T parsePartialDelimitedFrom(
1818       T defaultInstance, InputStream input, ExtensionRegistryLite extensionRegistry)
1819       throws InvalidProtocolBufferException {
1820     int size;
1821     try {
1822       int firstByte = input.read();
1823       if (firstByte == -1) {
1824         return null;
1825       }
1826       size = CodedInputStream.readRawVarint32(firstByte, input);
1827     } catch (IOException e) {
1828       throw new InvalidProtocolBufferException(e.getMessage());
1829     }
1830     InputStream limitedInput = new LimitedInputStream(input, size);
1831     CodedInputStream codedInput = CodedInputStream.newInstance(limitedInput);
1832     T message = parsePartialFrom(defaultInstance, codedInput, extensionRegistry);
1833     try {
1834       codedInput.checkLastTagWas(0);
1835     } catch (InvalidProtocolBufferException e) {
1836       throw e.setUnfinishedMessage(message);
1837     }
1838     return message;
1839   }
1840 }
1841