Merge "Add android.util.proto package as an @TestApi."

This commit is contained in:
Joe Onorato
2016-10-14 17:41:07 +00:00
committed by Android (Google) Code Review
14 changed files with 3321 additions and 0 deletions

View File

@@ -41027,6 +41027,156 @@ package android.util {
}
package android.util.proto {
public final class EncodedBuffer {
ctor public EncodedBuffer();
ctor public EncodedBuffer(int);
method public void dumpBuffers(java.lang.String);
method public static void dumpByteString(java.lang.String, java.lang.String, byte[]);
method public void editRawFixed32(int, int);
method public byte[] getBytes(int);
method public int getChunkCount();
method public java.lang.String getDebugString();
method public int getRawFixed32At(int);
method public static int getRawVarint32Size(int);
method public static int getRawVarint64Size(long);
method public static int getRawZigZag32Size(int);
method public static int getRawZigZag64Size(long);
method public int getReadPos();
method public int getReadableSize();
method public int getWriteBufIndex();
method public int getWriteIndex();
method public int getWritePos();
method public byte readRawByte();
method public int readRawFixed32();
method public long readRawUnsigned();
method public void rewindRead();
method public void rewindWriteTo(int);
method public void skipRead(int);
method public void startEditing();
method public void writeFromThisBuffer(int, int);
method public void writeRawBuffer(byte[]);
method public void writeRawBuffer(byte[], int, int);
method public void writeRawByte(byte);
method public void writeRawFixed32(int);
method public void writeRawFixed64(long);
method public void writeRawVarint32(int);
method public void writeRawVarint64(long);
method public void writeRawZigZag32(int);
method public void writeRawZigZag64(long);
}
public final class ProtoOutputStream {
ctor public ProtoOutputStream();
ctor public ProtoOutputStream(int);
method public static int checkFieldId(long, long);
method public static int convertObjectIdToOrdinal(int);
method public void dump(java.lang.String);
method public void endObject(long);
method public void endRepeatedObject(long);
method public byte[] getBytes();
method public static int getDepthFromToken(long);
method public static int getObjectIdFromToken(long);
method public static boolean getRepeatedFromToken(long);
method public static int getSizePosFromToken(long);
method public static int getTagSizeFromToken(long);
method public static long makeFieldId(int, long);
method public static long makeToken(int, boolean, int, int, int);
method public long startObject(long);
method public long startRepeatedObject(long);
method public static java.lang.String token2String(long);
method public void writeBool(long, boolean);
method public void writeBytes(long, byte[]);
method public void writeDouble(long, double);
method public void writeEnum(long, int);
method public void writeFixed32(long, int);
method public void writeFixed64(long, long);
method public void writeFloat(long, float);
method public void writeInt32(long, int);
method public void writeInt64(long, long);
method public void writePackedBool(long, boolean[]);
method public void writePackedDouble(long, double[]);
method public void writePackedEnum(long, int[]);
method public void writePackedFixed32(long, int[]);
method public void writePackedFixed64(long, long[]);
method public void writePackedFloat(long, float[]);
method public void writePackedInt32(long, int[]);
method public void writePackedInt64(long, long[]);
method public void writePackedSFixed32(long, int[]);
method public void writePackedSFixed64(long, long[]);
method public void writePackedSInt32(long, int[]);
method public void writePackedSInt64(long, long[]);
method public void writePackedUInt32(long, int[]);
method public void writePackedUInt64(long, long[]);
method public void writeRepeatedBool(long, boolean);
method public void writeRepeatedBytes(long, byte[]);
method public void writeRepeatedDouble(long, double);
method public void writeRepeatedEnum(long, int);
method public void writeRepeatedFixed32(long, int);
method public void writeRepeatedFixed64(long, long);
method public void writeRepeatedFloat(long, float);
method public void writeRepeatedInt32(long, int);
method public void writeRepeatedInt64(long, long);
method public void writeRepeatedSFixed32(long, int);
method public void writeRepeatedSFixed64(long, long);
method public void writeRepeatedSInt32(long, int);
method public void writeRepeatedSInt64(long, long);
method public void writeRepeatedString(long, java.lang.String);
method public void writeRepeatedUInt32(long, int);
method public void writeRepeatedUInt64(long, long);
method public void writeSFixed32(long, int);
method public void writeSFixed64(long, long);
method public void writeSInt32(long, int);
method public void writeSInt64(long, long);
method public void writeString(long, java.lang.String);
method public void writeTag(int, int);
method public void writeUInt32(long, int);
method public void writeUInt64(long, long);
field public static final long FIELD_COUNT_MASK = 16492674416640L; // 0xf0000000000L
field public static final long FIELD_COUNT_PACKED = 5497558138880L; // 0x50000000000L
field public static final long FIELD_COUNT_REPEATED = 2199023255552L; // 0x20000000000L
field public static final int FIELD_COUNT_SHIFT = 40; // 0x28
field public static final long FIELD_COUNT_SINGLE = 1099511627776L; // 0x10000000000L
field public static final long FIELD_COUNT_UNKNOWN = 0L; // 0x0L
field public static final int FIELD_ID_MASK = -8; // 0xfffffff8
field public static final int FIELD_ID_SHIFT = 3; // 0x3
field public static final long FIELD_TYPE_BOOL = 55834574848L; // 0xd00000000L
field public static final long FIELD_TYPE_BYTES = 64424509440L; // 0xf00000000L
field public static final long FIELD_TYPE_DOUBLE = 4294967296L; // 0x100000000L
field public static final long FIELD_TYPE_ENUM = 68719476736L; // 0x1000000000L
field public static final long FIELD_TYPE_FIXED32 = 38654705664L; // 0x900000000L
field public static final long FIELD_TYPE_FIXED64 = 42949672960L; // 0xa00000000L
field public static final long FIELD_TYPE_FLOAT = 8589934592L; // 0x200000000L
field public static final long FIELD_TYPE_INT32 = 12884901888L; // 0x300000000L
field public static final long FIELD_TYPE_INT64 = 17179869184L; // 0x400000000L
field public static final long FIELD_TYPE_MASK = 1095216660480L; // 0xff00000000L
field public static final long FIELD_TYPE_OBJECT = 73014444032L; // 0x1100000000L
field public static final long FIELD_TYPE_SFIXED32 = 47244640256L; // 0xb00000000L
field public static final long FIELD_TYPE_SFIXED64 = 51539607552L; // 0xc00000000L
field public static final int FIELD_TYPE_SHIFT = 32; // 0x20
field public static final long FIELD_TYPE_SINT32 = 30064771072L; // 0x700000000L
field public static final long FIELD_TYPE_SINT64 = 34359738368L; // 0x800000000L
field public static final long FIELD_TYPE_STRING = 60129542144L; // 0xe00000000L
field public static final long FIELD_TYPE_UINT32 = 21474836480L; // 0x500000000L
field public static final long FIELD_TYPE_UINT64 = 25769803776L; // 0x600000000L
field public static final long FIELD_TYPE_UNKNOWN = 0L; // 0x0L
field public static final java.lang.String TAG = "ProtoOutputStream";
field public static final int WIRE_TYPE_END_GROUP = 4; // 0x4
field public static final int WIRE_TYPE_FIXED32 = 5; // 0x5
field public static final int WIRE_TYPE_FIXED64 = 1; // 0x1
field public static final int WIRE_TYPE_LENGTH_DELIMITED = 2; // 0x2
field public static final int WIRE_TYPE_MASK = 7; // 0x7
field public static final int WIRE_TYPE_START_GROUP = 3; // 0x3
field public static final int WIRE_TYPE_VARINT = 0; // 0x0
}
public class ProtoParseException extends java.lang.RuntimeException {
ctor public ProtoParseException(java.lang.String);
}
}
package android.view {
public abstract class AbsSavedState implements android.os.Parcelable {

View File

@@ -0,0 +1,678 @@
/*
* Copyright (C) 2012 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package android.util.proto;
import android.annotation.TestApi;
import android.util.Log;
import java.util.ArrayList;
/**
* A stream of bytes containing a read pointer and a write pointer,
* backed by a set of fixed-size buffers. There are write functions for the
* primitive types stored by protocol buffers, but none of the logic
* for tags, inner objects, or any of that.
*
* Terminology:
* *Pos: Position in the whole data set (as if it were a single buffer).
* *Index: Position within a buffer.
* *BufIndex: Index of a buffer within the mBuffers list
* @hide
*/
@TestApi
public final class EncodedBuffer {
private static final String TAG = "EncodedBuffer";
private final ArrayList<byte[]> mBuffers = new ArrayList<byte[]>();
private final int mChunkSize;
/**
* The number of buffers in mBuffers. Stored separately to avoid the extra
* function call to size() everywhere for bounds checking.
*/
private int mBufferCount;
/**
* The buffer we are currently writing to.
*/
private byte[] mWriteBuffer;
/**
* The index into mWriteBuffer that we will write to next.
* It may point to the end of the buffer, in which case,
* the NEXT write will allocate a new buffer.
*/
private int mWriteIndex;
/**
* The index of mWriteBuffer in mBuffers.
*/
private int mWriteBufIndex;
/**
* The buffer we are currently reading from.
*/
private byte[] mReadBuffer;
/**
* The index of mReadBuffer in mBuffers.
*/
private int mReadBufIndex;
/**
* The index into mReadBuffer that we will read from next.
* It may point to the end of the buffer, in which case,
* the NEXT read will advance to the next buffer.
*/
private int mReadIndex;
/**
* The amount of data in the last buffer.
*/
private int mReadLimit = -1;
/**
* How much data there is total.
*/
private int mReadableSize = -1;
public EncodedBuffer() {
this(0);
}
/**
* Construct an EncodedBuffer object.
*
* @param chunkSize The size of the buffers to use. If chunkSize &lt;= 0, a default
* size will be used instead.
*/
public EncodedBuffer(int chunkSize) {
if (chunkSize <= 0) {
chunkSize = 8 * 1024;
}
mChunkSize = chunkSize;
mWriteBuffer = new byte[mChunkSize];
mBuffers.add(mWriteBuffer);
mBufferCount = 1;
}
//
// Buffer management.
//
/**
* Rewind the read and write pointers, and record how much data was last written.
*/
public void startEditing() {
mReadableSize = ((mWriteBufIndex) * mChunkSize) + mWriteIndex;
mReadLimit = mWriteIndex;
mWriteBuffer = mBuffers.get(0);
mWriteIndex = 0;
mWriteBufIndex = 0;
mReadBuffer = mWriteBuffer;
mReadBufIndex = 0;
mReadIndex = 0;
}
/**
* Rewind the read pointer. Don't touch the write pointer.
*/
public void rewindRead() {
mReadBuffer = mBuffers.get(0);
mReadBufIndex = 0;
mReadIndex = 0;
}
/**
* Only valid after startEditing. Returns -1 before that.
*/
public int getReadableSize() {
return mReadableSize;
}
//
// Reading from the read position.
//
/**
* Only valid after startEditing.
*/
public int getReadPos() {
return ((mReadBufIndex) * mChunkSize) + mReadIndex;
}
/**
* Skip over _amount_ bytes.
*/
public void skipRead(int amount) {
if (amount < 0) {
throw new RuntimeException("skipRead with negative amount=" + amount);
}
if (amount == 0) {
return;
}
if (amount <= mChunkSize - mReadIndex) {
mReadIndex += amount;
} else {
amount -= mChunkSize - mReadIndex;
mReadIndex = amount % mChunkSize;
if (mReadIndex == 0) {
mReadIndex = mChunkSize;
mReadBufIndex += (amount / mChunkSize);
} else {
mReadBufIndex += 1 + (amount / mChunkSize);
}
mReadBuffer = mBuffers.get(mReadBufIndex);
}
}
/**
* Read one byte from the stream and advance the read pointer.
*
* @throws IndexOutOfBoundsException if the read point is past the end of
* the buffer or past the read limit previously set by startEditing().
*/
public byte readRawByte() {
if (mReadBufIndex > mBufferCount
|| (mReadBufIndex == mBufferCount - 1 && mReadIndex >= mReadLimit)) {
throw new IndexOutOfBoundsException("Trying to read too much data"
+ " mReadBufIndex=" + mReadBufIndex + " mBufferCount=" + mBufferCount
+ " mReadIndex=" + mReadIndex + " mReadLimit=" + mReadLimit);
}
if (mReadIndex >= mChunkSize) {
mReadBufIndex++;
mReadBuffer = mBuffers.get(mReadBufIndex);
mReadIndex = 0;
}
return mReadBuffer[mReadIndex++];
}
/**
* Read an unsigned varint. The value will be returend in a java signed long.
*/
public long readRawUnsigned() {
int bits = 0;
long result = 0;
while (true) {
final byte b = readRawByte();
result |= ((long)(b & 0x7F)) << bits;
if ((b & 0x80) == 0) {
return result;
}
bits += 7;
if (bits > 64) {
throw new ProtoParseException("Varint too long -- " + getDebugString());
}
}
}
/**
* Read 32 little endian bits from the stream.
*/
public int readRawFixed32() {
return (readRawByte() & 0x0ff)
| ((readRawByte() & 0x0ff) << 8)
| ((readRawByte() & 0x0ff) << 16)
| ((readRawByte() & 0x0ff) << 24);
}
//
// Writing at a the end of the stream.
//
/**
* Advance to the next write buffer, allocating it if necessary.
*
* Must be called immediately <b>before</b> the next write, not after a write,
* so that a dangling empty buffer is not created. Doing so will interfere
* with the expectation that mWriteIndex will point past the end of the buffer
* until the next read happens.
*/
private void nextWriteBuffer() {
mWriteBufIndex++;
if (mWriteBufIndex >= mBufferCount) {
mWriteBuffer = new byte[mChunkSize];
mBuffers.add(mWriteBuffer);
mBufferCount++;
} else {
mWriteBuffer = mBuffers.get(mWriteBufIndex);
}
mWriteIndex = 0;
}
/**
* Write a single byte to the stream.
*/
public void writeRawByte(byte val) {
if (mWriteIndex >= mChunkSize) {
nextWriteBuffer();
}
mWriteBuffer[mWriteIndex++] = val;
}
/**
* Return how many bytes a 32 bit unsigned varint will take when written to the stream.
*/
public static int getRawVarint32Size(int val) {
if ((val & (0xffffffff << 7)) == 0) return 1;
if ((val & (0xffffffff << 14)) == 0) return 2;
if ((val & (0xffffffff << 21)) == 0) return 3;
if ((val & (0xffffffff << 28)) == 0) return 4;
return 5;
}
/**
* Write an unsigned varint to the stream. A signed value would need to take 10 bytes.
*
* @param val treated as unsigned.
*/
public void writeRawVarint32(int val) {
while (true) {
if ((val & ~0x7F) == 0) {
writeRawByte((byte)val);
return;
} else {
writeRawByte((byte)((val & 0x7F) | 0x80));
val >>>= 7;
}
}
}
/**
* Return how many bytes a 32 bit signed zig zag value will take when written to the stream.
*/
public static int getRawZigZag32Size(int val) {
return getRawVarint32Size(zigZag32(val));
}
/**
* Write a zig-zag encoded value.
*
* @param val treated as signed
*/
public void writeRawZigZag32(int val) {
writeRawVarint32(zigZag32(val));
}
/**
* Return how many bytes a 64 bit varint will take when written to the stream.
*/
public static int getRawVarint64Size(long val) {
if ((val & (0xffffffffffffffffL << 7)) == 0) return 1;
if ((val & (0xffffffffffffffffL << 14)) == 0) return 2;
if ((val & (0xffffffffffffffffL << 21)) == 0) return 3;
if ((val & (0xffffffffffffffffL << 28)) == 0) return 4;
if ((val & (0xffffffffffffffffL << 35)) == 0) return 5;
if ((val & (0xffffffffffffffffL << 42)) == 0) return 6;
if ((val & (0xffffffffffffffffL << 49)) == 0) return 7;
if ((val & (0xffffffffffffffffL << 56)) == 0) return 8;
if ((val & (0xffffffffffffffffL << 63)) == 0) return 9;
return 10;
}
/**
* Write a 64 bit varint to the stream.
*/
public void writeRawVarint64(long val) {
while (true) {
if ((val & ~0x7FL) == 0) {
writeRawByte((byte)val);
return;
} else {
writeRawByte((byte)((val & 0x7F) | 0x80));
val >>>= 7;
}
}
}
/**
* Return how many bytes a signed 64 bit zig zag value will take when written to the stream.
*/
public static int getRawZigZag64Size(long val) {
return getRawVarint64Size(zigZag64(val));
}
/**
* Write a 64 bit signed zig zag value to the stream.
*/
public void writeRawZigZag64(long val) {
writeRawVarint64(zigZag64(val));
}
/**
* Write 4 little endian bytes to the stream.
*/
public void writeRawFixed32(int val) {
writeRawByte((byte)(val));
writeRawByte((byte)(val >> 8));
writeRawByte((byte)(val >> 16));
writeRawByte((byte)(val >> 24));
}
/**
* Write 8 little endian bytes to the stream.
*/
public void writeRawFixed64(long val) {
writeRawByte((byte)(val));
writeRawByte((byte)(val >> 8));
writeRawByte((byte)(val >> 16));
writeRawByte((byte)(val >> 24));
writeRawByte((byte)(val >> 32));
writeRawByte((byte)(val >> 40));
writeRawByte((byte)(val >> 48));
writeRawByte((byte)(val >> 56));
}
/**
* Write a buffer to the stream. Writes nothing if val is null or zero-length.
*/
public void writeRawBuffer(byte[] val) {
if (val != null && val.length > 0) {
writeRawBuffer(val, 0, val.length);
}
}
/**
* Write part of an array of bytes.
*/
public void writeRawBuffer(byte[] val, int offset, int length) {
if (val == null) {
return;
}
// Write up to the amount left in the first chunk to write.
int amt = length < (mChunkSize - mWriteIndex) ? length : (mChunkSize - mWriteIndex);
if (amt > 0) {
System.arraycopy(val, offset, mWriteBuffer, mWriteIndex, amt);
mWriteIndex += amt;
length -= amt;
offset += amt;
}
while (length > 0) {
// We know we're now at the beginning of a chunk
nextWriteBuffer();
amt = length < mChunkSize ? length : mChunkSize;
System.arraycopy(val, offset, mWriteBuffer, mWriteIndex, amt);
mWriteIndex += amt;
length -= amt;
offset += amt;
}
}
/**
* Copies data _size_ bytes of data within this buffer from _srcOffset_
* to the current write position. Like memmov but handles the chunked buffer.
*/
public void writeFromThisBuffer(int srcOffset, int size) {
if (mReadLimit < 0) {
throw new IllegalStateException("writeFromThisBuffer before startEditing");
}
if (srcOffset < getWritePos()) {
throw new IllegalArgumentException("Can only move forward in the buffer --"
+ " srcOffset=" + srcOffset + " size=" + size + " " + getDebugString());
}
if (srcOffset + size > mReadableSize) {
throw new IllegalArgumentException("Trying to move more data than there is --"
+ " srcOffset=" + srcOffset + " size=" + size + " " + getDebugString());
}
if (size == 0) {
return;
}
if (srcOffset == ((mWriteBufIndex) * mChunkSize) + mWriteIndex /* write pos */) {
// Writing to the same location. Just advance the write pointer. We already
// checked that size is in bounds, so we don't need to do any more range
// checking.
if (size <= mChunkSize - mWriteIndex) {
mWriteIndex += size;
} else {
size -= mChunkSize - mWriteIndex;
mWriteIndex = size % mChunkSize;
if (mWriteIndex == 0) {
// Roll it back so nextWriteBuffer can do its job
// on the next call (also makes mBuffers.get() not
// fail if we're at the end).
mWriteIndex = mChunkSize;
mWriteBufIndex += (size / mChunkSize);
} else {
mWriteBufIndex += 1 + (size / mChunkSize);
}
mWriteBuffer = mBuffers.get(mWriteBufIndex);
}
} else {
// Loop through the buffer, copying as much as we can each time.
// We already bounds checked so we don't need to do it again here,
// and nextWriteBuffer will never allocate.
int readBufIndex = srcOffset / mChunkSize;
byte[] readBuffer = mBuffers.get(readBufIndex);
int readIndex = srcOffset % mChunkSize;
while (size > 0) {
if (mWriteIndex >= mChunkSize) {
nextWriteBuffer();
}
if (readIndex >= mChunkSize) {
readBufIndex++;
readBuffer = mBuffers.get(readBufIndex);
readIndex = 0;
}
final int spaceInWriteBuffer = mChunkSize - mWriteIndex;
final int availableInReadBuffer = mChunkSize - readIndex;
final int amt = Math.min(size, Math.min(spaceInWriteBuffer, availableInReadBuffer));
System.arraycopy(readBuffer, readIndex, mWriteBuffer, mWriteIndex, amt);
mWriteIndex += amt;
readIndex += amt;
size -= amt;
}
}
}
//
// Writing at a particular location.
//
/**
* Returns the index into the virtual array of the write pointer.
*/
public int getWritePos() {
return ((mWriteBufIndex) * mChunkSize) + mWriteIndex;
}
/**
* Resets the write pointer to a virtual location as returned by getWritePos.
*/
public void rewindWriteTo(int writePos) {
if (writePos > getWritePos()) {
throw new RuntimeException("rewindWriteTo only can go backwards" + writePos);
}
mWriteBufIndex = writePos / mChunkSize;
mWriteIndex = writePos % mChunkSize;
if (mWriteIndex == 0 && mWriteBufIndex != 0) {
// Roll back so nextWriteBuffer can do its job on the next call
// but at the first write we're at 0.
mWriteIndex = mChunkSize;
mWriteBufIndex--;
}
mWriteBuffer = mBuffers.get(mWriteBufIndex);
}
/**
* Read a 32 bit value from the stream.
*
* Doesn't touch or affect mWritePos.
*/
public int getRawFixed32At(int pos) {
return (0x00ff & (int)mBuffers.get(pos / mChunkSize)[pos % mChunkSize])
| ((0x0ff & (int)mBuffers.get((pos+1) / mChunkSize)[(pos+1) % mChunkSize]) << 8)
| ((0x0ff & (int)mBuffers.get((pos+2) / mChunkSize)[(pos+2) % mChunkSize]) << 16)
| ((0x0ff & (int)mBuffers.get((pos+3) / mChunkSize)[(pos+3) % mChunkSize]) << 24);
}
/**
* Overwrite a 32 bit value in the stream.
*
* Doesn't touch or affect mWritePos.
*/
public void editRawFixed32(int pos, int val) {
mBuffers.get(pos / mChunkSize)[pos % mChunkSize] = (byte)(val);
mBuffers.get((pos+1) / mChunkSize)[(pos+1) % mChunkSize] = (byte)(val >> 8);
mBuffers.get((pos+2) / mChunkSize)[(pos+2) % mChunkSize] = (byte)(val >> 16);
mBuffers.get((pos+3) / mChunkSize)[(pos+3) % mChunkSize] = (byte)(val >> 24);
}
//
// Zigging and zagging
//
/**
* Zig-zag encode a 32 bit value.
*/
private static int zigZag32(int val) {
return (val << 1) ^ (val >> 31);
}
/**
* Zig-zag encode a 64 bit value.
*/
private static long zigZag64(long val) {
return (val << 1) ^ (val >> 63);
}
//
// Debugging / testing
//
// VisibleForTesting
/**
* Get a copy of the first _size_ bytes of data. This is not range
* checked, and if the bounds are outside what has been written you will
* get garbage and if it is outside the buffers that have been allocated,
* you will get an exception.
*/
public byte[] getBytes(int size) {
final byte[] result = new byte[size];
final int bufCount = size / mChunkSize;
int bufIndex;
int writeIndex = 0;
for (bufIndex=0; bufIndex<bufCount; bufIndex++) {
System.arraycopy(mBuffers.get(bufIndex), 0, result, writeIndex, mChunkSize);
writeIndex += mChunkSize;
}
final int lastSize = size - (bufCount * mChunkSize);
if (lastSize > 0) {
System.arraycopy(mBuffers.get(bufIndex), 0, result, writeIndex, lastSize);
}
return result;
}
/**
* Get the number of chunks allocated.
*/
// VisibleForTesting
public int getChunkCount() {
return mBuffers.size();
}
/**
* Get the write position inside the current write chunk.
*/
// VisibleForTesting
public int getWriteIndex() {
return mWriteIndex;
}
/**
* Get the index of the current write chunk in the list of chunks.
*/
// VisibleForTesting
public int getWriteBufIndex() {
return mWriteBufIndex;
}
/**
* Return debugging information about this EncodedBuffer object.
*/
public String getDebugString() {
return "EncodedBuffer( mChunkSize=" + mChunkSize + " mBuffers.size=" + mBuffers.size()
+ " mBufferCount=" + mBufferCount + " mWriteIndex=" + mWriteIndex
+ " mWriteBufIndex=" + mWriteBufIndex + " mReadBufIndex=" + mReadBufIndex
+ " mReadIndex=" + mReadIndex + " mReadableSize=" + mReadableSize
+ " mReadLimit=" + mReadLimit + " )";
}
/**
* Print the internal buffer chunks.
*/
public void dumpBuffers(String tag) {
final int N = mBuffers.size();
int start = 0;
for (int i=0; i<N; i++) {
start += dumpByteString(tag, "{" + i + "} ", start, mBuffers.get(i));
}
}
/**
* Print the internal buffer chunks.
*/
public static void dumpByteString(String tag, String prefix, byte[] buf) {
dumpByteString(tag, prefix, 0, buf);
}
/**
* Print the internal buffer chunks.
*/
private static int dumpByteString(String tag, String prefix, int start, byte[] buf) {
StringBuffer sb = new StringBuffer();
final int length = buf.length;
final int lineLen = 16;
int i;
for (i=0; i<length; i++) {
if (i % lineLen == 0) {
if (i != 0) {
Log.d(tag, sb.toString());
sb = new StringBuffer();
}
sb.append(prefix);
sb.append('[');
sb.append(start + i);
sb.append(']');
sb.append(' ');
} else {
sb.append(' ');
}
byte b = buf[i];
byte c = (byte)((b >> 4) & 0x0f);
if (c < 10) {
sb.append((char)('0' + c));
} else {
sb.append((char)('a' - 10 + c));
}
byte d = (byte)(b & 0x0f);
if (d < 10) {
sb.append((char)('0' + d));
} else {
sb.append((char)('a' - 10 + d));
}
}
Log.d(tag, sb.toString());
return length;
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,38 @@
/*
* Copyright (C) 2012 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package android.util.proto;
import android.annotation.TestApi;
/**
* Thrown when there is an error parsing protobuf data.
*
* @hide
*/
@TestApi
public class ProtoParseException extends RuntimeException {
/**
* Construct a ProtoParseException.
*
* @param msg The message.
*/
public ProtoParseException(String msg) {
super(msg);
}
}

View File

@@ -0,0 +1,5 @@
<body>
Provides utility classes to export protocol buffers from the system.
{@hide}
</body>

View File

@@ -0,0 +1,41 @@
#
# Copyright (C) 2015 The Android Open Source Project
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
LOCAL_PATH:= $(call my-dir)
# ==========================================================
# Build the host executable: protoc-gen-javastream
# ==========================================================
include $(CLEAR_VARS)
LOCAL_MODULE := protoc-gen-javastream
LOCAL_SRC_FILES := \
Errors.cpp \
string_utils.cpp \
main.cpp
LOCAL_SHARED_LIBRARIES := \
libprotoc
include $(BUILD_HOST_EXECUTABLE)
# ==========================================================
# Build the java test
# ==========================================================
include $(CLEAR_VARS)
LOCAL_SRC_FILES := \
$(call all-java-files-under, test) \
$(call all-proto-files-under, test)
LOCAL_MODULE := StreamingProtoTest
LOCAL_PROTOC_OPTIMIZE_TYPE := stream
include $(BUILD_JAVA_LIBRARY)

View File

@@ -0,0 +1,87 @@
#include "Errors.h"
#include <stdlib.h>
namespace android {
namespace javastream_proto {
Errors ERRORS;
const string UNKNOWN_FILE;
const int UNKNOWN_LINE = 0;
Error::Error()
{
}
Error::Error(const Error& that)
:filename(that.filename),
lineno(that.lineno),
message(that.message)
{
}
Error::Error(const string& f, int l, const char* m)
:filename(f),
lineno(l),
message(m)
{
}
Errors::Errors()
:m_errors()
{
}
Errors::~Errors()
{
}
void
Errors::Add(const string& filename, int lineno, const char* format, ...)
{
va_list args;
va_start(args, format);
AddImpl(filename, lineno, format, args);
va_end(args);
}
void
Errors::AddImpl(const string& filename, int lineno, const char* format, va_list args)
{
va_list args2;
va_copy(args2, args);
int message_size = vsnprintf((char*)NULL, 0, format, args2);
va_end(args2);
char* buffer = new char[message_size+1];
vsnprintf(buffer, message_size, format, args);
Error error(filename, lineno, buffer);
delete[] buffer;
m_errors.push_back(error);
}
void
Errors::Print() const
{
for (vector<Error>::const_iterator it = m_errors.begin(); it != m_errors.end(); it++) {
if (it->filename == UNKNOWN_FILE) {
fprintf(stderr, "%s", it->message.c_str());
} else if (it->lineno == UNKNOWN_LINE) {
fprintf(stderr, "%s:%s", it->filename.c_str(), it->message.c_str());
} else {
fprintf(stderr, "%s:%d:%s", it->filename.c_str(), it->lineno, it->message.c_str());
}
}
}
bool
Errors::HasErrors() const
{
return m_errors.size() > 0;
}
} // namespace javastream_proto
} // namespace android

View File

@@ -0,0 +1,48 @@
#include <stdio.h>
#include <string>
#include <vector>
namespace android {
namespace javastream_proto {
using namespace std;
struct Error
{
Error();
explicit Error(const Error& that);
Error(const string& filename, int lineno, const char* message);
string filename;
int lineno;
string message;
};
class Errors
{
public:
Errors();
~Errors();
// Add an error
void Add(const string& filename, int lineno, const char* format, ...);
// Print the errors to stderr if there are any.
void Print() const;
bool HasErrors() const;
private:
// The errors that have been added
vector<Error> m_errors;
void AddImpl(const string& filename, int lineno, const char* format, va_list ap);
};
extern Errors ERRORS;
extern const string UNKNOWN_FILE;
extern const int UNKNOWN_LINE;
} // namespace javastream_proto
} // namespace android

View File

@@ -0,0 +1,391 @@
#include "Errors.h"
#include "string_utils.h"
#include "google/protobuf/compiler/plugin.pb.h"
#include "google/protobuf/io/zero_copy_stream_impl.h"
#include "google/protobuf/text_format.h"
#include <stdio.h>
#include <iomanip>
#include <iostream>
#include <sstream>
#include <map>
using namespace android::javastream_proto;
using namespace google::protobuf;
using namespace google::protobuf::compiler;
using namespace google::protobuf::io;
using namespace std;
const int FIELD_TYPE_SHIFT = 32;
const uint64_t FIELD_TYPE_DOUBLE = 1L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_FLOAT = 2L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_INT32 = 3L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_INT64 = 4L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_UINT32 = 5L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_UINT64 = 6L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_SINT32 = 7L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_SINT64 = 8L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_FIXED32 = 9L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_FIXED64 = 10L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_SFIXED32 = 11L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_SFIXED64 = 12L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_BOOL = 13L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_STRING = 14L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_BYTES = 15L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_ENUM = 16L << FIELD_TYPE_SHIFT;
const uint64_t FIELD_TYPE_OBJECT = 17L << FIELD_TYPE_SHIFT;
const int FIELD_COUNT_SHIFT = 40;
const uint64_t FIELD_COUNT_SINGLE = 1L << FIELD_COUNT_SHIFT;
const uint64_t FIELD_COUNT_REPEATED = 2L << FIELD_COUNT_SHIFT;
const uint64_t FIELD_COUNT_PACKED = 5L << FIELD_COUNT_SHIFT;
/**
* See if this is the file for this request, and not one of the imported ones.
*/
static bool
should_generate_for_file(const CodeGeneratorRequest& request, const string& file)
{
const int N = request.file_to_generate_size();
for (int i=0; i<N; i++) {
if (request.file_to_generate(i) == file) {
return true;
}
}
return false;
}
/**
* If the descriptor gives us a class name, use that. Otherwise make one up from
* the filename of the .proto file.
*/
static string
make_outer_class_name(const FileDescriptorProto& file_descriptor)
{
string name = file_descriptor.options().java_outer_classname();
if (name.size() == 0) {
name = to_camel_case(file_base_name(file_descriptor.name()));
if (name.size() == 0) {
ERRORS.Add(UNKNOWN_FILE, UNKNOWN_LINE,
"Unable to make an outer class name for file: %s",
file_descriptor.name().c_str());
name = "Unknown";
}
}
return name;
}
/**
* Figure out the package name that we are generating.
*/
static string
make_java_package(const FileDescriptorProto& file_descriptor) {
if (file_descriptor.options().has_java_package()) {
return file_descriptor.options().java_package();
} else {
return file_descriptor.package();
}
}
/**
* Figure out the name of the file we are generating.
*/
static string
make_file_name(const FileDescriptorProto& file_descriptor)
{
string const package = make_java_package(file_descriptor);
string result;
if (package.size() > 0) {
result = replace_string(package, '.', '/');
result += '/';
}
result += make_outer_class_name(file_descriptor);
result += ".java";
return result;
}
static string
indent_more(const string& indent)
{
return indent + " ";
}
/**
* Write the constants for an enum.
*/
static void
write_enum(stringstream& text, const EnumDescriptorProto& enu, const string& indent)
{
const int N = enu.value_size();
text << indent << "// enum " << enu.name() << endl;
for (int i=0; i<N; i++) {
const EnumValueDescriptorProto& value = enu.value(i);
text << indent << "public static final int "
<< make_constant_name(value.name())
<< " = " << value.number() << ";" << endl;
}
text << endl;
}
/**
* Get the string name for a field.
*/
static string
get_proto_type(const FieldDescriptorProto& field)
{
switch (field.type()) {
case FieldDescriptorProto::TYPE_DOUBLE:
return "double";
case FieldDescriptorProto::TYPE_FLOAT:
return "float";
case FieldDescriptorProto::TYPE_INT64:
return "int64";
case FieldDescriptorProto::TYPE_UINT64:
return "uint64";
case FieldDescriptorProto::TYPE_INT32:
return "int32";
case FieldDescriptorProto::TYPE_FIXED64:
return "fixed64";
case FieldDescriptorProto::TYPE_FIXED32:
return "fixed32";
case FieldDescriptorProto::TYPE_BOOL:
return "bool";
case FieldDescriptorProto::TYPE_STRING:
return "string";
case FieldDescriptorProto::TYPE_GROUP:
return "group<unsupported!>";
case FieldDescriptorProto::TYPE_MESSAGE:
return field.type_name();
case FieldDescriptorProto::TYPE_BYTES:
return "bytes";
case FieldDescriptorProto::TYPE_UINT32:
return "uint32";
case FieldDescriptorProto::TYPE_ENUM:
return field.type_name();
case FieldDescriptorProto::TYPE_SFIXED32:
return "sfixed32";
case FieldDescriptorProto::TYPE_SFIXED64:
return "sfixed64";
case FieldDescriptorProto::TYPE_SINT32:
return "sint32";
case FieldDescriptorProto::TYPE_SINT64:
return "sint64";
default:
// won't happen
return "void";
}
}
static uint64_t
get_field_id(const FieldDescriptorProto& field)
{
// Number
uint64_t result = (uint32_t)field.number();
// Type
switch (field.type()) {
case FieldDescriptorProto::TYPE_DOUBLE:
result |= FIELD_TYPE_DOUBLE;
case FieldDescriptorProto::TYPE_FLOAT:
result |= FIELD_TYPE_FLOAT;
case FieldDescriptorProto::TYPE_INT64:
result |= FIELD_TYPE_INT64;
case FieldDescriptorProto::TYPE_UINT64:
result |= FIELD_TYPE_UINT64;
case FieldDescriptorProto::TYPE_INT32:
result |= FIELD_TYPE_INT32;
case FieldDescriptorProto::TYPE_FIXED64:
result |= FIELD_TYPE_FIXED64;
case FieldDescriptorProto::TYPE_FIXED32:
result |= FIELD_TYPE_FIXED32;
case FieldDescriptorProto::TYPE_BOOL:
result |= FIELD_TYPE_BOOL;
case FieldDescriptorProto::TYPE_STRING:
result |= FIELD_TYPE_STRING;
case FieldDescriptorProto::TYPE_MESSAGE:
result |= FIELD_TYPE_OBJECT;
case FieldDescriptorProto::TYPE_BYTES:
result |= FIELD_TYPE_BYTES;
case FieldDescriptorProto::TYPE_UINT32:
result |= FIELD_TYPE_UINT32;
case FieldDescriptorProto::TYPE_ENUM:
result |= FIELD_TYPE_ENUM;
case FieldDescriptorProto::TYPE_SFIXED32:
result |= FIELD_TYPE_SFIXED32;
case FieldDescriptorProto::TYPE_SFIXED64:
result |= FIELD_TYPE_SFIXED64;
case FieldDescriptorProto::TYPE_SINT32:
result |= FIELD_TYPE_SINT32;
case FieldDescriptorProto::TYPE_SINT64:
result |= FIELD_TYPE_SINT64;
default:
;
}
// Count
if (field.options().packed()) {
result |= FIELD_COUNT_PACKED;
} else if (field.label() == FieldDescriptorProto::LABEL_REPEATED) {
result |= FIELD_COUNT_REPEATED;
} else {
result |= FIELD_COUNT_SINGLE;
}
return result;
}
/**
* Write a field.
*/
static void
write_field(stringstream& text, const FieldDescriptorProto& field, const string& indent)
{
string optional_comment = field.label() == FieldDescriptorProto::LABEL_OPTIONAL
? "optional " : "";
string repeated_comment = field.label() == FieldDescriptorProto::LABEL_REPEATED
? "repeated " : "";
string proto_type = get_proto_type(field);
string packed_comment = field.options().packed()
? " [packed=true]" : "";
text << indent << "// " << optional_comment << repeated_comment << proto_type << ' '
<< field.name() << " = " << field.number() << packed_comment << ';' << endl;
text << indent << "public static final long " << make_constant_name(field.name()) << " = 0x";
ios::fmtflags fmt(text.flags());
text << setfill('0') << setw(16) << hex << get_field_id(field);
text.flags(fmt);
text << "L;" << endl;
text << endl;
}
/**
* Write a Message constants class.
*/
static void
write_message(stringstream& text, const DescriptorProto& message, const string& indent)
{
int N;
const string indented = indent_more(indent);
text << indent << "// message " << message.name() << endl;
text << indent << "public final class " << message.name() << " {" << endl;
text << endl;
// Enums
N = message.enum_type_size();
for (int i=0; i<N; i++) {
write_enum(text, message.enum_type(i), indented);
}
// Nested classes
N = message.nested_type_size();
for (int i=0; i<N; i++) {
write_message(text, message.nested_type(i), indented);
}
// Fields
N = message.field_size();
for (int i=0; i<N; i++) {
write_field(text, message.field(i), indented);
}
text << indent << "}" << endl;
text << endl;
}
/**
* Write the contents of a file.
*/
static void
write_file(stringstream& text, const FileDescriptorProto& file_descriptor)
{
string const package_name = make_java_package(file_descriptor);
string const outer_class_name = make_outer_class_name(file_descriptor);
text << "// Generated by protoc-gen-javastream. DO NOT MODIFY." << endl;
text << "// source: " << file_descriptor.name() << endl << endl;
if (package_name.size() > 0) {
if (package_name.size() > 0) {
text << "package " << package_name << ";" << endl;
text << endl;
}
}
// This bit of policy is android api rules specific: Raw proto classes
// must never be in the API, but they should all be available for testing.
text << "/** @hide */" << endl;
text << "@android.annotation.TestApi" << endl;
text << "public final class " << outer_class_name << " {" << endl;
text << endl;
int N;
const string indented = indent_more("");
N = file_descriptor.enum_type_size();
for (int i=0; i<N; i++) {
write_enum(text, file_descriptor.enum_type(i), indented);
}
N = file_descriptor.message_type_size();
for (int i=0; i<N; i++) {
write_message(text, file_descriptor.message_type(i), indented);
}
text << "}" << endl;
}
/**
* Main.
*/
int
main(int argc, char const*const* argv)
{
(void)argc;
(void)argv;
GOOGLE_PROTOBUF_VERIFY_VERSION;
CodeGeneratorRequest request;
CodeGeneratorResponse response;
// Read the request
request.ParseFromIstream(&cin);
// Build the files we need.
const int N = request.proto_file_size();
for (int i=0; i<N; i++) {
const FileDescriptorProto& file_descriptor = request.proto_file(i);
if (should_generate_for_file(request, file_descriptor.name())) {
// Generate the text
stringstream text;
write_file(text, file_descriptor);
// Put the text in the response
CodeGeneratorResponse::File* file_response = response.add_file();
file_response->set_name(make_file_name(file_descriptor));
file_response->set_content(text.str());
cerr << "writing file: " << file_response->name() << endl;
}
}
// If we had errors, don't write the response. Print the errors and exit.
if (ERRORS.HasErrors()) {
ERRORS.Print();
return 1;
}
// If we didn't have errors, write the response and exit happily.
response.SerializeToOstream(&cout);
return 0;
}

View File

@@ -0,0 +1,95 @@
#include "string_utils.h"
#include <iostream>
namespace android {
namespace javastream_proto {
using namespace std;
string
to_camel_case(const string& str)
{
string result;
const int N = str.size();
result.reserve(N);
bool capitalize_next = true;
for (int i=0; i<N; i++) {
char c = str[i];
if (c == '_') {
capitalize_next = true;
} else {
if (capitalize_next && c >= 'a' && c <= 'z') {
c = 'A' + c - 'a';
capitalize_next = false;
} else if (c >= 'A' && c <= 'Z') {
capitalize_next = false;
} else if (c >= '0' && c <= '9') {
capitalize_next = true;
} else {
// All other characters (e.g. non-latin) count as capital.
capitalize_next = false;
}
result += c;
}
}
return result;
}
string
make_constant_name(const string& str)
{
string result;
const int N = str.size();
bool underscore_next = false;
for (int i=0; i<N; i++) {
char c = str[i];
if (c >= 'A' && c <= 'Z') {
if (underscore_next) {
result += '_';
underscore_next = false;
}
} else if (c >= 'a' && c <= 'z') {
c = 'A' + c - 'a';
underscore_next = true;
} else if (c == '_') {
underscore_next = false;
}
result += c;
}
return result;
}
string
file_base_name(const string& str)
{
size_t start = str.rfind('/');
if (start == string::npos) {
start = 0;
} else {
start++;
}
size_t end = str.find('.', start);
if (end == string::npos) {
end = str.size();
}
return str.substr(start, end-start);
}
string
replace_string(const string& str, const char replace, const char with)
{
string result(str);
const int N = result.size();
for (int i=0; i<N; i++) {
if (result[i] == replace) {
result[i] = with;
}
}
return result;
}
} // namespace javastream_proto
} // namespace android

View File

@@ -0,0 +1,32 @@
#include <string>
namespace android {
namespace javastream_proto {
using namespace std;
/**
* Capitalizes the string, removes underscores and makes the next letter
* capitalized, and makes the letter following numbers capitalized.
*/
string to_camel_case(const string& str);
/**
* Capitalize and insert underscores for CamelCase.
*/
string make_constant_name(const string& str);
/**
* Returns the part of a file name that isn't a path and isn't a type suffix.
*/
string file_base_name(const string& str);
/**
* Replace all occurances of 'replace' with 'with'.
*/
string replace_string(const string& str, const char replace, const char with);
} // namespace javastream_proto
} // namespace android

View File

@@ -0,0 +1,26 @@
/*
* Copyright (C) 2016 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
syntax = "proto2";
package com.android.streaming_proto_test;
/**
* Message that is used from the other file.
*/
message ImportedMessage {
optional int32 data = 1;
};

View File

@@ -0,0 +1,7 @@
package com.android.streaming_proto_test;
public class Main {
public void main(String[] argv) {
System.out.println("hello world");
}
}

View File

@@ -0,0 +1,124 @@
/*
* Copyright (C) 2016 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
syntax = "proto2";
import "frameworks/base/tools/streaming_proto/test/imported.proto";
package com.android.streaming_proto_test;
/**
* Enum that outside the scope of any classes.
*/
enum Outside {
OUTSIDE_0 = 0;
OUTSIDE_1 = 1;
};
message Sibling {
optional int32 int32_field = 1;
}
/**
* Message with all of the field types.
*/
message All {
/**
* Enum that is inside the scope of a class.
*/
enum Inside {
option allow_alias = true;
INSIDE_0 = 0;
INSIDE_1 = 1;
INSIDE_1A = 1;
};
/**
* Message that is recursive.
*/
message Nested {
optional int32 data = 10001;
optional Nested nested = 10002;
};
optional double double_field = 10;
repeated double double_field_repeated = 11;
repeated double double_field_packed = 12 [packed=true];
optional float float_field = 20;
repeated float float_field_repeated = 21;
repeated float float_field_packed = 22 [packed=true];
optional int32 int32_field = 30;
repeated int32 int32_field_repeated = 31;
repeated int32 int32_field_packed = 32 [packed=true];
optional int64 int64_field = 40;
repeated int64 int64_field_repeated = 41;
repeated int64 int64_field_packed = 42 [packed=true];
optional uint32 uint32_field = 50;
repeated uint32 uint32_field_repeated = 51;
repeated uint32 uint32_field_packed = 52 [packed=true];
optional uint64 uint64_field = 60;
repeated uint64 uint64_field_repeated = 61;
repeated uint64 uint64_field_packed = 62 [packed=true];
optional sint32 sint32_field = 70;
repeated sint32 sint32_field_repeated = 71;
repeated sint32 sint32_field_packed = 72 [packed=true];
optional sint64 sint64_field = 80;
repeated sint64 sint64_field_repeated = 81;
repeated sint64 sint64_field_packed = 82 [packed=true];
optional fixed32 fixed32_field = 90;
repeated fixed32 fixed32_field_repeated = 91;
repeated fixed32 fixed32_field_packed = 92 [packed=true];
optional fixed64 fixed64_field = 100;
repeated fixed64 fixed64_field_repeated = 101;
repeated fixed64 fixed64_field_packed = 102 [packed=true];
optional sfixed32 sfixed32_field = 110;
repeated sfixed32 sfixed32_field_repeated = 111;
repeated sfixed32 sfixed32_field_packed = 112 [packed=true];
optional sfixed64 sfixed64_field = 120;
repeated sfixed64 sfixed64_field_repeated = 121;
repeated sfixed64 sfixed64_field_packed = 122 [packed=true];
optional bool bool_field = 130;
repeated bool bool_field_repeated = 131;
repeated bool bool_field_packed = 132 [packed=true];
optional string string_field = 140;
repeated string string_field_repeated = 141;
optional bytes bytes_field = 150;
repeated bytes bytes_field_repeated = 151;
optional Outside outside_field = 160;
repeated Outside outside_field_repeated = 161;
repeated Outside outside_field_packed = 162 [packed=true];
optional Nested nested_field = 170;
repeated Nested nested_field_repeated = 171;
optional ImportedMessage imported_field = 180;
repeated ImportedMessage imported_field_repeated = 181;
};