123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190 |
- // Protocol Buffers - Google's data interchange format
- // Copyright 2013 Google Inc. All rights reserved.
- // https://developers.google.com/protocol-buffers/
- //
- // Redistribution and use in source and binary forms, with or without
- // modification, are permitted provided that the following conditions are
- // met:
- //
- // * Redistributions of source code must retain the above copyright
- // notice, this list of conditions and the following disclaimer.
- // * Redistributions in binary form must reproduce the above
- // copyright notice, this list of conditions and the following disclaimer
- // in the documentation and/or other materials provided with the
- // distribution.
- // * Neither the name of Google Inc. nor the names of its
- // contributors may be used to endorse or promote products derived from
- // this software without specific prior written permission.
- //
- // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- package com.google.protobuf.nano;
- import java.io.IOException;
- import java.util.Arrays;
- /**
- * Abstract interface implemented by Protocol Message objects.
- *
- * @author wink@google.com Wink Saville
- */
- public abstract class MessageNano {
- protected volatile int cachedSize = -1;
- /**
- * Get the number of bytes required to encode this message.
- * Returns the cached size or calls getSerializedSize which
- * sets the cached size. This is used internally when serializing
- * so the size is only computed once. If a member is modified
- * then this could be stale call getSerializedSize if in doubt.
- */
- public int getCachedSize() {
- if (cachedSize < 0) {
- // getSerializedSize sets cachedSize
- getSerializedSize();
- }
- return cachedSize;
- }
- /**
- * Computes the number of bytes required to encode this message.
- * The size is cached and the cached result can be retrieved
- * using getCachedSize().
- */
- public int getSerializedSize() {
- int size = computeSerializedSize();
- cachedSize = size;
- return size;
- }
- /**
- * Computes the number of bytes required to encode this message. This does not update the
- * cached size.
- */
- protected int computeSerializedSize() {
- // This is overridden if the generated message has serialized fields.
- return 0;
- }
- /**
- * Serializes the message and writes it to {@code output}.
- *
- * @param output the output to receive the serialized form.
- * @throws IOException if an error occurred writing to {@code output}.
- */
- public void writeTo(CodedOutputByteBufferNano output) throws IOException {
- // Does nothing by default. Overridden by subclasses which have data to write.
- }
- /**
- * Parse {@code input} as a message of this type and merge it with the
- * message being built.
- */
- public abstract MessageNano mergeFrom(CodedInputByteBufferNano input) throws IOException;
- /**
- * Serialize to a byte array.
- * @return byte array with the serialized data.
- */
- public static final byte[] toByteArray(MessageNano msg) {
- final byte[] result = new byte[msg.getSerializedSize()];
- toByteArray(msg, result, 0, result.length);
- return result;
- }
- /**
- * Serialize to a byte array starting at offset through length. The
- * method getSerializedSize must have been called prior to calling
- * this method so the proper length is know. If an attempt to
- * write more than length bytes OutOfSpaceException will be thrown
- * and if length bytes are not written then IllegalStateException
- * is thrown.
- */
- public static final void toByteArray(MessageNano msg, byte[] data, int offset, int length) {
- try {
- final CodedOutputByteBufferNano output =
- CodedOutputByteBufferNano.newInstance(data, offset, length);
- msg.writeTo(output);
- output.checkNoSpaceLeft();
- } catch (IOException e) {
- throw new RuntimeException("Serializing to a byte array threw an IOException "
- + "(should never happen).", e);
- }
- }
- /**
- * Parse {@code data} as a message of this type and merge it with the
- * message being built.
- */
- public static final <T extends MessageNano> T mergeFrom(T msg, final byte[] data)
- throws InvalidProtocolBufferNanoException {
- return mergeFrom(msg, data, 0, data.length);
- }
- /**
- * Parse {@code data} as a message of this type and merge it with the
- * message being built.
- */
- public static final <T extends MessageNano> T mergeFrom(T msg, final byte[] data,
- final int off, final int len) throws InvalidProtocolBufferNanoException {
- try {
- final CodedInputByteBufferNano input =
- CodedInputByteBufferNano.newInstance(data, off, len);
- msg.mergeFrom(input);
- input.checkLastTagWas(0);
- return msg;
- } catch (InvalidProtocolBufferNanoException e) {
- throw e;
- } catch (IOException e) {
- throw new RuntimeException("Reading from a byte array threw an IOException (should "
- + "never happen).");
- }
- }
- /**
- * Compares two {@code MessageNano}s and returns true if the message's are the same class and
- * have serialized form equality (i.e. all of the field values are the same).
- */
- public static final boolean messageNanoEquals(MessageNano a, MessageNano b) {
- if (a == b) {
- return true;
- }
- if (a == null || b == null) {
- return false;
- }
- if (a.getClass() != b.getClass()) {
- return false;
- }
- final int serializedSize = a.getSerializedSize();
- if (b.getSerializedSize() != serializedSize) {
- return false;
- }
- final byte[] aByteArray = new byte[serializedSize];
- final byte[] bByteArray = new byte[serializedSize];
- toByteArray(a, aByteArray, 0, serializedSize);
- toByteArray(b, bByteArray, 0, serializedSize);
- return Arrays.equals(aByteArray, bByteArray);
- }
- /**
- * Returns a string that is (mostly) compatible with ProtoBuffer's TextFormat. Note that groups
- * (which are deprecated) are not serialized with the correct field name.
- *
- * <p>This is implemented using reflection, so it is not especially fast nor is it guaranteed
- * to find all fields if you have method removal turned on for proguard.
- */
- @Override
- public String toString() {
- return MessageNanoPrinter.print(this);
- }
- }
|