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 static com.google.protobuf.ArrayDecoders.decodeBoolList; 34 import static com.google.protobuf.ArrayDecoders.decodeBytes; 35 import static com.google.protobuf.ArrayDecoders.decodeBytesList; 36 import static com.google.protobuf.ArrayDecoders.decodeDouble; 37 import static com.google.protobuf.ArrayDecoders.decodeDoubleList; 38 import static com.google.protobuf.ArrayDecoders.decodeExtensionOrUnknownField; 39 import static com.google.protobuf.ArrayDecoders.decodeFixed32; 40 import static com.google.protobuf.ArrayDecoders.decodeFixed32List; 41 import static com.google.protobuf.ArrayDecoders.decodeFixed64; 42 import static com.google.protobuf.ArrayDecoders.decodeFixed64List; 43 import static com.google.protobuf.ArrayDecoders.decodeFloat; 44 import static com.google.protobuf.ArrayDecoders.decodeFloatList; 45 import static com.google.protobuf.ArrayDecoders.decodeGroupList; 46 import static com.google.protobuf.ArrayDecoders.decodeMessageField; 47 import static com.google.protobuf.ArrayDecoders.decodeMessageList; 48 import static com.google.protobuf.ArrayDecoders.decodePackedBoolList; 49 import static com.google.protobuf.ArrayDecoders.decodePackedDoubleList; 50 import static com.google.protobuf.ArrayDecoders.decodePackedFixed32List; 51 import static com.google.protobuf.ArrayDecoders.decodePackedFixed64List; 52 import static com.google.protobuf.ArrayDecoders.decodePackedFloatList; 53 import static com.google.protobuf.ArrayDecoders.decodePackedSInt32List; 54 import static com.google.protobuf.ArrayDecoders.decodePackedSInt64List; 55 import static com.google.protobuf.ArrayDecoders.decodePackedVarint32List; 56 import static com.google.protobuf.ArrayDecoders.decodePackedVarint64List; 57 import static com.google.protobuf.ArrayDecoders.decodeSInt32List; 58 import static com.google.protobuf.ArrayDecoders.decodeSInt64List; 59 import static com.google.protobuf.ArrayDecoders.decodeString; 60 import static com.google.protobuf.ArrayDecoders.decodeStringList; 61 import static com.google.protobuf.ArrayDecoders.decodeStringListRequireUtf8; 62 import static com.google.protobuf.ArrayDecoders.decodeStringRequireUtf8; 63 import static com.google.protobuf.ArrayDecoders.decodeUnknownField; 64 import static com.google.protobuf.ArrayDecoders.decodeVarint32; 65 import static com.google.protobuf.ArrayDecoders.decodeVarint32List; 66 import static com.google.protobuf.ArrayDecoders.decodeVarint64; 67 import static com.google.protobuf.ArrayDecoders.decodeVarint64List; 68 import static com.google.protobuf.ArrayDecoders.mergeGroupField; 69 import static com.google.protobuf.ArrayDecoders.mergeMessageField; 70 import static com.google.protobuf.ArrayDecoders.skipField; 71 72 import com.google.protobuf.ArrayDecoders.Registers; 73 import com.google.protobuf.ByteString.CodedBuilder; 74 import com.google.protobuf.FieldSet.FieldDescriptorLite; 75 import com.google.protobuf.Internal.EnumVerifier; 76 import com.google.protobuf.Internal.ProtobufList; 77 import com.google.protobuf.MapEntryLite.Metadata; 78 import java.io.IOException; 79 import java.lang.reflect.Field; 80 import java.util.Arrays; 81 import java.util.Iterator; 82 import java.util.List; 83 import java.util.Map; 84 85 /** Schema used for standard messages. */ 86 final class MessageSchema<T> implements Schema<T> { 87 private static final int INTS_PER_FIELD = 3; 88 private static final int OFFSET_BITS = 20; 89 private static final int OFFSET_MASK = 0XFFFFF; 90 private static final int FIELD_TYPE_MASK = 0x0FF00000; 91 private static final int REQUIRED_MASK = 0x10000000; 92 private static final int ENFORCE_UTF8_MASK = 0x20000000; 93 private static final int NO_PRESENCE_SENTINEL = -1 & OFFSET_MASK; 94 private static final int[] EMPTY_INT_ARRAY = new int[0]; 95 96 /** An offset applied to the field type ID for scalar fields that are a member of a oneof. */ 97 static final int ONEOF_TYPE_OFFSET = 51 /* FieldType.MAP + 1 */; 98 99 /** 100 * Keep a direct reference to the unsafe object so we don't need to go through the UnsafeUtil 101 * wrapper for every call. 102 */ 103 private static final sun.misc.Unsafe UNSAFE = UnsafeUtil.getUnsafe(); 104 105 /** 106 * Holds all information for accessing the message fields. The layout is as follows (field 107 * positions are relative to the offset of the start of the field in the buffer): 108 * 109 * <p> 110 * 111 * <pre> 112 * [ 0 - 3] unused 113 * [ 4 - 31] field number 114 * [32 - 33] unused 115 * [34 - 34] whether UTF-8 enforcement should be applied to a string field. 116 * [35 - 35] whether the field is required 117 * [36 - 43] field type / for oneof: field type + {@link #ONEOF_TYPE_OFFSET} 118 * [44 - 63] field offset / oneof value field offset 119 * [64 - 69] unused 120 * [70 - 75] field presence mask shift (unused for oneof/repeated fields) 121 * [76 - 95] presence field offset / oneof case field offset / cached size field offset 122 * </pre> 123 * 124 * Note that presence field offset can only use 20 bits - 1. All bits set to 1 is the sentinel 125 * value for non-presence. This is not validated at runtime, we simply assume message layouts 126 * will not exceed 1MB (assuming ~10 bytes per field, that implies 100k fields which should hit 127 * other javac limits first). 128 */ 129 private final int[] buffer; 130 131 /** 132 * Holds object references for fields. For each field entry in {@code buffer}, there are two 133 * corresponding entries in this array. The content is different from different field types: 134 * 135 * <pre> 136 * Map fields: 137 * objects[pos] = map default entry instance 138 * objects[pos + 1] = EnumVerifier if map value is enum, or message class reference if map 139 * value is message. 140 * Message fields: 141 * objects[pos] = null or cached message schema 142 * objects[pos + 1] = message class reference 143 * Enum fields: 144 * objects[pos] = null 145 * objects[pos + 1] = EnumVerifier 146 * </pre> 147 */ 148 private final Object[] objects; 149 150 private final int minFieldNumber; 151 private final int maxFieldNumber; 152 153 private final MessageLite defaultInstance; 154 private final boolean hasExtensions; 155 private final boolean lite; 156 private final boolean proto3; 157 // TODO(xiaofeng): Make both full-runtime and lite-runtime support cached field size. 158 private final boolean useCachedSizeField; 159 160 /** Represents [checkInitialized positions, map field positions, repeated field offsets]. */ 161 private final int[] intArray; 162 163 /** 164 * Values at indices 0 -> checkInitializedCount in intArray are positions to check for 165 * initialization. 166 */ 167 private final int checkInitializedCount; 168 169 /** 170 * Values at indices checkInitializedCount -> repeatedFieldOffsetStart are map positions. 171 * Everything after that are repeated field offsets. 172 */ 173 private final int repeatedFieldOffsetStart; 174 175 private final NewInstanceSchema newInstanceSchema; 176 private final ListFieldSchema listFieldSchema; 177 private final UnknownFieldSchema<?, ?> unknownFieldSchema; 178 private final ExtensionSchema<?> extensionSchema; 179 private final MapFieldSchema mapFieldSchema; 180 MessageSchema( int[] buffer, Object[] objects, int minFieldNumber, int maxFieldNumber, MessageLite defaultInstance, boolean proto3, boolean useCachedSizeField, int[] intArray, int checkInitialized, int mapFieldPositions, NewInstanceSchema newInstanceSchema, ListFieldSchema listFieldSchema, UnknownFieldSchema<?, ?> unknownFieldSchema, ExtensionSchema<?> extensionSchema, MapFieldSchema mapFieldSchema)181 private MessageSchema( 182 int[] buffer, 183 Object[] objects, 184 int minFieldNumber, 185 int maxFieldNumber, 186 MessageLite defaultInstance, 187 boolean proto3, 188 boolean useCachedSizeField, 189 int[] intArray, 190 int checkInitialized, 191 int mapFieldPositions, 192 NewInstanceSchema newInstanceSchema, 193 ListFieldSchema listFieldSchema, 194 UnknownFieldSchema<?, ?> unknownFieldSchema, 195 ExtensionSchema<?> extensionSchema, 196 MapFieldSchema mapFieldSchema) { 197 this.buffer = buffer; 198 this.objects = objects; 199 this.minFieldNumber = minFieldNumber; 200 this.maxFieldNumber = maxFieldNumber; 201 202 this.lite = defaultInstance instanceof GeneratedMessageLite; 203 this.proto3 = proto3; 204 this.hasExtensions = extensionSchema != null && extensionSchema.hasExtensions(defaultInstance); 205 this.useCachedSizeField = useCachedSizeField; 206 207 this.intArray = intArray; 208 this.checkInitializedCount = checkInitialized; 209 this.repeatedFieldOffsetStart = mapFieldPositions; 210 211 this.newInstanceSchema = newInstanceSchema; 212 this.listFieldSchema = listFieldSchema; 213 this.unknownFieldSchema = unknownFieldSchema; 214 this.extensionSchema = extensionSchema; 215 this.defaultInstance = defaultInstance; 216 this.mapFieldSchema = mapFieldSchema; 217 } 218 newSchema( Class<T> messageClass, MessageInfo messageInfo, NewInstanceSchema newInstanceSchema, ListFieldSchema listFieldSchema, UnknownFieldSchema<?, ?> unknownFieldSchema, ExtensionSchema<?> extensionSchema, MapFieldSchema mapFieldSchema)219 static <T> MessageSchema<T> newSchema( 220 Class<T> messageClass, 221 MessageInfo messageInfo, 222 NewInstanceSchema newInstanceSchema, 223 ListFieldSchema listFieldSchema, 224 UnknownFieldSchema<?, ?> unknownFieldSchema, 225 ExtensionSchema<?> extensionSchema, 226 MapFieldSchema mapFieldSchema) { 227 if (messageInfo instanceof RawMessageInfo) { 228 return newSchemaForRawMessageInfo( 229 (RawMessageInfo) messageInfo, 230 newInstanceSchema, 231 listFieldSchema, 232 unknownFieldSchema, 233 extensionSchema, 234 mapFieldSchema); 235 236 } else { 237 return newSchemaForMessageInfo( 238 (StructuralMessageInfo) messageInfo, 239 newInstanceSchema, 240 listFieldSchema, 241 unknownFieldSchema, 242 extensionSchema, 243 mapFieldSchema); 244 } 245 } 246 newSchemaForRawMessageInfo( RawMessageInfo messageInfo, NewInstanceSchema newInstanceSchema, ListFieldSchema listFieldSchema, UnknownFieldSchema<?, ?> unknownFieldSchema, ExtensionSchema<?> extensionSchema, MapFieldSchema mapFieldSchema)247 static <T> MessageSchema<T> newSchemaForRawMessageInfo( 248 RawMessageInfo messageInfo, 249 NewInstanceSchema newInstanceSchema, 250 ListFieldSchema listFieldSchema, 251 UnknownFieldSchema<?, ?> unknownFieldSchema, 252 ExtensionSchema<?> extensionSchema, 253 MapFieldSchema mapFieldSchema) { 254 final boolean isProto3 = messageInfo.getSyntax() == ProtoSyntax.PROTO3; 255 256 String info = messageInfo.getStringInfo(); 257 final int length = info.length(); 258 int i = 0; 259 260 int next = info.charAt(i++); 261 if (next >= 0xD800) { 262 int result = next & 0x1FFF; 263 int shift = 13; 264 while ((next = info.charAt(i++)) >= 0xD800) { 265 result |= (next & 0x1FFF) << shift; 266 shift += 13; 267 } 268 next = result | (next << shift); 269 } 270 final int unusedFlags = next; 271 272 next = info.charAt(i++); 273 if (next >= 0xD800) { 274 int result = next & 0x1FFF; 275 int shift = 13; 276 while ((next = info.charAt(i++)) >= 0xD800) { 277 result |= (next & 0x1FFF) << shift; 278 shift += 13; 279 } 280 next = result | (next << shift); 281 } 282 final int fieldCount = next; 283 284 final int oneofCount; 285 final int hasBitsCount; 286 final int minFieldNumber; 287 final int maxFieldNumber; 288 final int numEntries; 289 final int mapFieldCount; 290 final int repeatedFieldCount; 291 final int checkInitialized; 292 final int[] intArray; 293 int objectsPosition; 294 if (fieldCount == 0) { 295 oneofCount = 0; 296 hasBitsCount = 0; 297 minFieldNumber = 0; 298 maxFieldNumber = 0; 299 numEntries = 0; 300 mapFieldCount = 0; 301 repeatedFieldCount = 0; 302 checkInitialized = 0; 303 intArray = EMPTY_INT_ARRAY; 304 objectsPosition = 0; 305 } else { 306 next = info.charAt(i++); 307 if (next >= 0xD800) { 308 int result = next & 0x1FFF; 309 int shift = 13; 310 while ((next = info.charAt(i++)) >= 0xD800) { 311 result |= (next & 0x1FFF) << shift; 312 shift += 13; 313 } 314 next = result | (next << shift); 315 } 316 oneofCount = next; 317 318 next = info.charAt(i++); 319 if (next >= 0xD800) { 320 int result = next & 0x1FFF; 321 int shift = 13; 322 while ((next = info.charAt(i++)) >= 0xD800) { 323 result |= (next & 0x1FFF) << shift; 324 shift += 13; 325 } 326 next = result | (next << shift); 327 } 328 hasBitsCount = next; 329 330 next = info.charAt(i++); 331 if (next >= 0xD800) { 332 int result = next & 0x1FFF; 333 int shift = 13; 334 while ((next = info.charAt(i++)) >= 0xD800) { 335 result |= (next & 0x1FFF) << shift; 336 shift += 13; 337 } 338 next = result | (next << shift); 339 } 340 minFieldNumber = next; 341 342 next = info.charAt(i++); 343 if (next >= 0xD800) { 344 int result = next & 0x1FFF; 345 int shift = 13; 346 while ((next = info.charAt(i++)) >= 0xD800) { 347 result |= (next & 0x1FFF) << shift; 348 shift += 13; 349 } 350 next = result | (next << shift); 351 } 352 maxFieldNumber = next; 353 354 next = info.charAt(i++); 355 if (next >= 0xD800) { 356 int result = next & 0x1FFF; 357 int shift = 13; 358 while ((next = info.charAt(i++)) >= 0xD800) { 359 result |= (next & 0x1FFF) << shift; 360 shift += 13; 361 } 362 next = result | (next << shift); 363 } 364 numEntries = next; 365 366 next = info.charAt(i++); 367 if (next >= 0xD800) { 368 int result = next & 0x1FFF; 369 int shift = 13; 370 while ((next = info.charAt(i++)) >= 0xD800) { 371 result |= (next & 0x1FFF) << shift; 372 shift += 13; 373 } 374 next = result | (next << shift); 375 } 376 mapFieldCount = next; 377 378 next = info.charAt(i++); 379 if (next >= 0xD800) { 380 int result = next & 0x1FFF; 381 int shift = 13; 382 while ((next = info.charAt(i++)) >= 0xD800) { 383 result |= (next & 0x1FFF) << shift; 384 shift += 13; 385 } 386 next = result | (next << shift); 387 } 388 repeatedFieldCount = next; 389 390 next = info.charAt(i++); 391 if (next >= 0xD800) { 392 int result = next & 0x1FFF; 393 int shift = 13; 394 while ((next = info.charAt(i++)) >= 0xD800) { 395 result |= (next & 0x1FFF) << shift; 396 shift += 13; 397 } 398 next = result | (next << shift); 399 } 400 checkInitialized = next; 401 intArray = new int[checkInitialized + mapFieldCount + repeatedFieldCount]; 402 // Field objects are after a list of (oneof, oneofCase) pairs + a list of hasbits fields. 403 objectsPosition = oneofCount * 2 + hasBitsCount; 404 } 405 406 final sun.misc.Unsafe unsafe = UNSAFE; 407 final Object[] messageInfoObjects = messageInfo.getObjects(); 408 int checkInitializedPosition = 0; 409 final Class<?> messageClass = messageInfo.getDefaultInstance().getClass(); 410 int[] buffer = new int[numEntries * INTS_PER_FIELD]; 411 Object[] objects = new Object[numEntries * 2]; 412 413 int mapFieldIndex = checkInitialized; 414 int repeatedFieldIndex = checkInitialized + mapFieldCount; 415 416 int bufferIndex = 0; 417 while (i < length) { 418 final int fieldNumber; 419 final int fieldTypeWithExtraBits; 420 final int fieldType; 421 422 next = info.charAt(i++); 423 if (next >= 0xD800) { 424 int result = next & 0x1FFF; 425 int shift = 13; 426 while ((next = info.charAt(i++)) >= 0xD800) { 427 result |= (next & 0x1FFF) << shift; 428 shift += 13; 429 } 430 next = result | (next << shift); 431 } 432 fieldNumber = next; 433 434 next = info.charAt(i++); 435 if (next >= 0xD800) { 436 int result = next & 0x1FFF; 437 int shift = 13; 438 while ((next = info.charAt(i++)) >= 0xD800) { 439 result |= (next & 0x1FFF) << shift; 440 shift += 13; 441 } 442 next = result | (next << shift); 443 } 444 fieldTypeWithExtraBits = next; 445 fieldType = fieldTypeWithExtraBits & 0xFF; 446 447 if ((fieldTypeWithExtraBits & 0x400) != 0) { 448 intArray[checkInitializedPosition++] = bufferIndex; 449 } 450 451 final int fieldOffset; 452 final int presenceMaskShift; 453 final int presenceFieldOffset; 454 455 // Oneof 456 if (fieldType >= ONEOF_TYPE_OFFSET) { 457 next = info.charAt(i++); 458 if (next >= 0xD800) { 459 int result = next & 0x1FFF; 460 int shift = 13; 461 while ((next = info.charAt(i++)) >= 0xD800) { 462 result |= (next & 0x1FFF) << shift; 463 shift += 13; 464 } 465 next = result | (next << shift); 466 } 467 int oneofIndex = next; 468 469 final int oneofFieldType = fieldType - ONEOF_TYPE_OFFSET; 470 if (oneofFieldType == 9 /* FieldType.MESSAGE */ 471 || oneofFieldType == 17 /* FieldType.GROUP */) { 472 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = messageInfoObjects[objectsPosition++]; 473 } else if (oneofFieldType == 12 /* FieldType.ENUM */) { 474 if (!isProto3) { 475 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = messageInfoObjects[objectsPosition++]; 476 } 477 } 478 479 final java.lang.reflect.Field oneofField; 480 int index = oneofIndex * 2; 481 Object o = messageInfoObjects[index]; 482 if (o instanceof java.lang.reflect.Field) { 483 oneofField = (java.lang.reflect.Field) o; 484 } else { 485 oneofField = reflectField(messageClass, (String) o); 486 // Memoize java.lang.reflect.Field instances for oneof/hasbits fields, since they're 487 // potentially used for many Protobuf fields. Since there's a 1-1 mapping from the 488 // Protobuf field to the Java Field for non-oneofs, there's no benefit for memoizing 489 // those. 490 messageInfoObjects[index] = oneofField; 491 } 492 493 fieldOffset = (int) unsafe.objectFieldOffset(oneofField); 494 495 final java.lang.reflect.Field oneofCaseField; 496 index++; 497 o = messageInfoObjects[index]; 498 if (o instanceof java.lang.reflect.Field) { 499 oneofCaseField = (java.lang.reflect.Field) o; 500 } else { 501 oneofCaseField = reflectField(messageClass, (String) o); 502 messageInfoObjects[index] = oneofCaseField; 503 } 504 505 presenceFieldOffset = (int) unsafe.objectFieldOffset(oneofCaseField); 506 presenceMaskShift = 0; 507 } else { 508 Field field = reflectField(messageClass, (String) messageInfoObjects[objectsPosition++]); 509 if (fieldType == 9 /* FieldType.MESSAGE */ || fieldType == 17 /* FieldType.GROUP */) { 510 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = field.getType(); 511 } else if (fieldType == 27 /* FieldType.MESSAGE_LIST */ 512 || fieldType == 49 /* FieldType.GROUP_LIST */) { 513 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = messageInfoObjects[objectsPosition++]; 514 } else if (fieldType == 12 /* FieldType.ENUM */ 515 || fieldType == 30 /* FieldType.ENUM_LIST */ 516 || fieldType == 44 /* FieldType.ENUM_LIST_PACKED */) { 517 if (!isProto3) { 518 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = messageInfoObjects[objectsPosition++]; 519 } 520 } else if (fieldType == 50 /* FieldType.MAP */) { 521 intArray[mapFieldIndex++] = bufferIndex; 522 objects[bufferIndex / INTS_PER_FIELD * 2] = messageInfoObjects[objectsPosition++]; 523 if ((fieldTypeWithExtraBits & 0x800) != 0) { 524 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = messageInfoObjects[objectsPosition++]; 525 } 526 } 527 528 fieldOffset = (int) unsafe.objectFieldOffset(field); 529 boolean hasHasBit = (fieldTypeWithExtraBits & 0x1000) == 0x1000; 530 if (hasHasBit && fieldType <= 17 /* FieldType.GROUP */) { 531 next = info.charAt(i++); 532 if (next >= 0xD800) { 533 int result = next & 0x1FFF; 534 int shift = 13; 535 while ((next = info.charAt(i++)) >= 0xD800) { 536 result |= (next & 0x1FFF) << shift; 537 shift += 13; 538 } 539 next = result | (next << shift); 540 } 541 int hasBitsIndex = next; 542 543 final java.lang.reflect.Field hasBitsField; 544 int index = oneofCount * 2 + hasBitsIndex / 32; 545 Object o = messageInfoObjects[index]; 546 if (o instanceof java.lang.reflect.Field) { 547 hasBitsField = (java.lang.reflect.Field) o; 548 } else { 549 hasBitsField = reflectField(messageClass, (String) o); 550 messageInfoObjects[index] = hasBitsField; 551 } 552 553 presenceFieldOffset = (int) unsafe.objectFieldOffset(hasBitsField); 554 presenceMaskShift = hasBitsIndex % 32; 555 } else { 556 presenceFieldOffset = NO_PRESENCE_SENTINEL; 557 presenceMaskShift = 0; 558 } 559 560 if (fieldType >= 18 && fieldType <= 49) { 561 // Field types of repeated fields are in a consecutive range from 18 (DOUBLE_LIST) to 562 // 49 (GROUP_LIST). 563 intArray[repeatedFieldIndex++] = fieldOffset; 564 } 565 } 566 567 buffer[bufferIndex++] = fieldNumber; 568 buffer[bufferIndex++] = 569 ((fieldTypeWithExtraBits & 0x200) != 0 ? ENFORCE_UTF8_MASK : 0) 570 | ((fieldTypeWithExtraBits & 0x100) != 0 ? REQUIRED_MASK : 0) 571 | (fieldType << OFFSET_BITS) 572 | fieldOffset; 573 buffer[bufferIndex++] = (presenceMaskShift << OFFSET_BITS) | presenceFieldOffset; 574 } 575 576 return new MessageSchema<T>( 577 buffer, 578 objects, 579 minFieldNumber, 580 maxFieldNumber, 581 messageInfo.getDefaultInstance(), 582 isProto3, 583 /* useCachedSizeField= */ false, 584 intArray, 585 checkInitialized, 586 checkInitialized + mapFieldCount, 587 newInstanceSchema, 588 listFieldSchema, 589 unknownFieldSchema, 590 extensionSchema, 591 mapFieldSchema); 592 } 593 reflectField(Class<?> messageClass, String fieldName)594 private static java.lang.reflect.Field reflectField(Class<?> messageClass, String fieldName) { 595 try { 596 return messageClass.getDeclaredField(fieldName); 597 } catch (NoSuchFieldException e) { 598 // Some Samsung devices lie about what fields are present via the getDeclaredField API so 599 // we do the for loop properly that they seem to have messed up... 600 java.lang.reflect.Field[] fields = messageClass.getDeclaredFields(); 601 for (java.lang.reflect.Field field : fields) { 602 if (fieldName.equals(field.getName())) { 603 return field; 604 } 605 } 606 607 // If we make it here, the runtime still lies about what we know to be true at compile 608 // time. We throw to alert server monitoring for further remediation. 609 throw new RuntimeException( 610 "Field " 611 + fieldName 612 + " for " 613 + messageClass.getName() 614 + " not found. Known fields are " 615 + Arrays.toString(fields)); 616 } 617 } 618 newSchemaForMessageInfo( StructuralMessageInfo messageInfo, NewInstanceSchema newInstanceSchema, ListFieldSchema listFieldSchema, UnknownFieldSchema<?, ?> unknownFieldSchema, ExtensionSchema<?> extensionSchema, MapFieldSchema mapFieldSchema)619 static <T> MessageSchema<T> newSchemaForMessageInfo( 620 StructuralMessageInfo messageInfo, 621 NewInstanceSchema newInstanceSchema, 622 ListFieldSchema listFieldSchema, 623 UnknownFieldSchema<?, ?> unknownFieldSchema, 624 ExtensionSchema<?> extensionSchema, 625 MapFieldSchema mapFieldSchema) { 626 final boolean isProto3 = messageInfo.getSyntax() == ProtoSyntax.PROTO3; 627 FieldInfo[] fis = messageInfo.getFields(); 628 final int minFieldNumber; 629 final int maxFieldNumber; 630 if (fis.length == 0) { 631 minFieldNumber = 0; 632 maxFieldNumber = 0; 633 } else { 634 minFieldNumber = fis[0].getFieldNumber(); 635 maxFieldNumber = fis[fis.length - 1].getFieldNumber(); 636 } 637 638 final int numEntries = fis.length; 639 640 int[] buffer = new int[numEntries * INTS_PER_FIELD]; 641 Object[] objects = new Object[numEntries * 2]; 642 643 int mapFieldCount = 0; 644 int repeatedFieldCount = 0; 645 for (FieldInfo fi : fis) { 646 if (fi.getType() == FieldType.MAP) { 647 mapFieldCount++; 648 } else if (fi.getType().id() >= 18 && fi.getType().id() <= 49) { 649 // Field types of repeated fields are in a consecutive range from 18 (DOUBLE_LIST) to 650 // 49 (GROUP_LIST). 651 repeatedFieldCount++; 652 } 653 } 654 int[] mapFieldPositions = mapFieldCount > 0 ? new int[mapFieldCount] : null; 655 int[] repeatedFieldOffsets = repeatedFieldCount > 0 ? new int[repeatedFieldCount] : null; 656 mapFieldCount = 0; 657 repeatedFieldCount = 0; 658 659 int[] checkInitialized = messageInfo.getCheckInitialized(); 660 if (checkInitialized == null) { 661 checkInitialized = EMPTY_INT_ARRAY; 662 } 663 int checkInitializedIndex = 0; 664 // Fill in the manifest data from the descriptors. 665 int fieldIndex = 0; 666 for (int bufferIndex = 0; fieldIndex < fis.length; bufferIndex += INTS_PER_FIELD) { 667 final FieldInfo fi = fis[fieldIndex]; 668 final int fieldNumber = fi.getFieldNumber(); 669 670 // We found the entry for the next field. Store the entry in the manifest for 671 // this field and increment the field index. 672 storeFieldData(fi, buffer, bufferIndex, objects); 673 674 // Convert field number to index 675 if (checkInitializedIndex < checkInitialized.length 676 && checkInitialized[checkInitializedIndex] == fieldNumber) { 677 checkInitialized[checkInitializedIndex++] = bufferIndex; 678 } 679 680 if (fi.getType() == FieldType.MAP) { 681 mapFieldPositions[mapFieldCount++] = bufferIndex; 682 } else if (fi.getType().id() >= 18 && fi.getType().id() <= 49) { 683 // Field types of repeated fields are in a consecutive range from 18 (DOUBLE_LIST) to 684 // 49 (GROUP_LIST). 685 repeatedFieldOffsets[repeatedFieldCount++] = 686 (int) UnsafeUtil.objectFieldOffset(fi.getField()); 687 } 688 689 fieldIndex++; 690 } 691 692 if (mapFieldPositions == null) { 693 mapFieldPositions = EMPTY_INT_ARRAY; 694 } 695 if (repeatedFieldOffsets == null) { 696 repeatedFieldOffsets = EMPTY_INT_ARRAY; 697 } 698 int[] combined = 699 new int[checkInitialized.length + mapFieldPositions.length + repeatedFieldOffsets.length]; 700 System.arraycopy(checkInitialized, 0, combined, 0, checkInitialized.length); 701 System.arraycopy( 702 mapFieldPositions, 0, combined, checkInitialized.length, mapFieldPositions.length); 703 System.arraycopy( 704 repeatedFieldOffsets, 705 0, 706 combined, 707 checkInitialized.length + mapFieldPositions.length, 708 repeatedFieldOffsets.length); 709 710 return new MessageSchema<T>( 711 buffer, 712 objects, 713 minFieldNumber, 714 maxFieldNumber, 715 messageInfo.getDefaultInstance(), 716 isProto3, 717 /* useCachedSizeField= */ true, 718 combined, 719 checkInitialized.length, 720 checkInitialized.length + mapFieldPositions.length, 721 newInstanceSchema, 722 listFieldSchema, 723 unknownFieldSchema, 724 extensionSchema, 725 mapFieldSchema); 726 } 727 storeFieldData( FieldInfo fi, int[] buffer, int bufferIndex, Object[] objects)728 private static void storeFieldData( 729 FieldInfo fi, int[] buffer, int bufferIndex, Object[] objects) { 730 final int fieldOffset; 731 final int typeId; 732 final int presenceMaskShift; 733 final int presenceFieldOffset; 734 735 OneofInfo oneof = fi.getOneof(); 736 if (oneof != null) { 737 typeId = fi.getType().id() + ONEOF_TYPE_OFFSET; 738 fieldOffset = (int) UnsafeUtil.objectFieldOffset(oneof.getValueField()); 739 presenceFieldOffset = (int) UnsafeUtil.objectFieldOffset(oneof.getCaseField()); 740 presenceMaskShift = 0; 741 } else { 742 FieldType type = fi.getType(); 743 fieldOffset = (int) UnsafeUtil.objectFieldOffset(fi.getField()); 744 typeId = type.id(); 745 if (!type.isList() && !type.isMap()) { 746 Field presenceField = fi.getPresenceField(); 747 if (presenceField == null) { 748 presenceFieldOffset = NO_PRESENCE_SENTINEL; 749 } else { 750 presenceFieldOffset = (int) UnsafeUtil.objectFieldOffset(presenceField); 751 } 752 presenceMaskShift = Integer.numberOfTrailingZeros(fi.getPresenceMask()); 753 } else { 754 if (fi.getCachedSizeField() == null) { 755 presenceFieldOffset = 0; 756 presenceMaskShift = 0; 757 } else { 758 presenceFieldOffset = (int) UnsafeUtil.objectFieldOffset(fi.getCachedSizeField()); 759 presenceMaskShift = 0; 760 } 761 } 762 } 763 764 buffer[bufferIndex] = fi.getFieldNumber(); 765 buffer[bufferIndex + 1] = 766 (fi.isEnforceUtf8() ? ENFORCE_UTF8_MASK : 0) 767 | (fi.isRequired() ? REQUIRED_MASK : 0) 768 | (typeId << OFFSET_BITS) 769 | fieldOffset; 770 buffer[bufferIndex + 2] = (presenceMaskShift << OFFSET_BITS) | presenceFieldOffset; 771 772 Object messageFieldClass = fi.getMessageFieldClass(); 773 if (fi.getMapDefaultEntry() != null) { 774 objects[bufferIndex / INTS_PER_FIELD * 2] = fi.getMapDefaultEntry(); 775 if (messageFieldClass != null) { 776 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = messageFieldClass; 777 } else if (fi.getEnumVerifier() != null) { 778 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = fi.getEnumVerifier(); 779 } 780 } else { 781 if (messageFieldClass != null) { 782 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = messageFieldClass; 783 } else if (fi.getEnumVerifier() != null) { 784 objects[bufferIndex / INTS_PER_FIELD * 2 + 1] = fi.getEnumVerifier(); 785 } 786 } 787 } 788 789 @SuppressWarnings("unchecked") 790 @Override newInstance()791 public T newInstance() { 792 return (T) newInstanceSchema.newInstance(defaultInstance); 793 } 794 795 @Override equals(T message, T other)796 public boolean equals(T message, T other) { 797 final int bufferLength = buffer.length; 798 for (int pos = 0; pos < bufferLength; pos += INTS_PER_FIELD) { 799 if (!equals(message, other, pos)) { 800 return false; 801 } 802 } 803 804 Object messageUnknown = unknownFieldSchema.getFromMessage(message); 805 Object otherUnknown = unknownFieldSchema.getFromMessage(other); 806 if (!messageUnknown.equals(otherUnknown)) { 807 return false; 808 } 809 810 if (hasExtensions) { 811 FieldSet<?> messageExtensions = extensionSchema.getExtensions(message); 812 FieldSet<?> otherExtensions = extensionSchema.getExtensions(other); 813 return messageExtensions.equals(otherExtensions); 814 } 815 return true; 816 } 817 equals(T message, T other, int pos)818 private boolean equals(T message, T other, int pos) { 819 final int typeAndOffset = typeAndOffsetAt(pos); 820 final long offset = offset(typeAndOffset); 821 822 switch (type(typeAndOffset)) { 823 case 0: // DOUBLE: 824 return arePresentForEquals(message, other, pos) 825 && Double.doubleToLongBits(UnsafeUtil.getDouble(message, offset)) 826 == Double.doubleToLongBits(UnsafeUtil.getDouble(other, offset)); 827 case 1: // FLOAT: 828 return arePresentForEquals(message, other, pos) 829 && Float.floatToIntBits(UnsafeUtil.getFloat(message, offset)) 830 == Float.floatToIntBits(UnsafeUtil.getFloat(other, offset)); 831 case 2: // INT64: 832 return arePresentForEquals(message, other, pos) 833 && UnsafeUtil.getLong(message, offset) == UnsafeUtil.getLong(other, offset); 834 case 3: // UINT64: 835 return arePresentForEquals(message, other, pos) 836 && UnsafeUtil.getLong(message, offset) == UnsafeUtil.getLong(other, offset); 837 case 4: // INT32: 838 return arePresentForEquals(message, other, pos) 839 && UnsafeUtil.getInt(message, offset) == UnsafeUtil.getInt(other, offset); 840 case 5: // FIXED64: 841 return arePresentForEquals(message, other, pos) 842 && UnsafeUtil.getLong(message, offset) == UnsafeUtil.getLong(other, offset); 843 case 6: // FIXED32: 844 return arePresentForEquals(message, other, pos) 845 && UnsafeUtil.getInt(message, offset) == UnsafeUtil.getInt(other, offset); 846 case 7: // BOOL: 847 return arePresentForEquals(message, other, pos) 848 && UnsafeUtil.getBoolean(message, offset) == UnsafeUtil.getBoolean(other, offset); 849 case 8: // STRING: 850 return arePresentForEquals(message, other, pos) 851 && SchemaUtil.safeEquals( 852 UnsafeUtil.getObject(message, offset), UnsafeUtil.getObject(other, offset)); 853 case 9: // MESSAGE: 854 return arePresentForEquals(message, other, pos) 855 && SchemaUtil.safeEquals( 856 UnsafeUtil.getObject(message, offset), UnsafeUtil.getObject(other, offset)); 857 case 10: // BYTES: 858 return arePresentForEquals(message, other, pos) 859 && SchemaUtil.safeEquals( 860 UnsafeUtil.getObject(message, offset), UnsafeUtil.getObject(other, offset)); 861 case 11: // UINT32: 862 return arePresentForEquals(message, other, pos) 863 && UnsafeUtil.getInt(message, offset) == UnsafeUtil.getInt(other, offset); 864 case 12: // ENUM: 865 return arePresentForEquals(message, other, pos) 866 && UnsafeUtil.getInt(message, offset) == UnsafeUtil.getInt(other, offset); 867 case 13: // SFIXED32: 868 return arePresentForEquals(message, other, pos) 869 && UnsafeUtil.getInt(message, offset) == UnsafeUtil.getInt(other, offset); 870 case 14: // SFIXED64: 871 return arePresentForEquals(message, other, pos) 872 && UnsafeUtil.getLong(message, offset) == UnsafeUtil.getLong(other, offset); 873 case 15: // SINT32: 874 return arePresentForEquals(message, other, pos) 875 && UnsafeUtil.getInt(message, offset) == UnsafeUtil.getInt(other, offset); 876 case 16: // SINT64: 877 return arePresentForEquals(message, other, pos) 878 && UnsafeUtil.getLong(message, offset) == UnsafeUtil.getLong(other, offset); 879 case 17: // GROUP: 880 return arePresentForEquals(message, other, pos) 881 && SchemaUtil.safeEquals( 882 UnsafeUtil.getObject(message, offset), UnsafeUtil.getObject(other, offset)); 883 884 case 18: // DOUBLE_LIST: 885 case 19: // FLOAT_LIST: 886 case 20: // INT64_LIST: 887 case 21: // UINT64_LIST: 888 case 22: // INT32_LIST: 889 case 23: // FIXED64_LIST: 890 case 24: // FIXED32_LIST: 891 case 25: // BOOL_LIST: 892 case 26: // STRING_LIST: 893 case 27: // MESSAGE_LIST: 894 case 28: // BYTES_LIST: 895 case 29: // UINT32_LIST: 896 case 30: // ENUM_LIST: 897 case 31: // SFIXED32_LIST: 898 case 32: // SFIXED64_LIST: 899 case 33: // SINT32_LIST: 900 case 34: // SINT64_LIST: 901 case 35: // DOUBLE_LIST_PACKED: 902 case 36: // FLOAT_LIST_PACKED: 903 case 37: // INT64_LIST_PACKED: 904 case 38: // UINT64_LIST_PACKED: 905 case 39: // INT32_LIST_PACKED: 906 case 40: // FIXED64_LIST_PACKED: 907 case 41: // FIXED32_LIST_PACKED: 908 case 42: // BOOL_LIST_PACKED: 909 case 43: // UINT32_LIST_PACKED: 910 case 44: // ENUM_LIST_PACKED: 911 case 45: // SFIXED32_LIST_PACKED: 912 case 46: // SFIXED64_LIST_PACKED: 913 case 47: // SINT32_LIST_PACKED: 914 case 48: // SINT64_LIST_PACKED: 915 case 49: // GROUP_LIST: 916 return SchemaUtil.safeEquals( 917 UnsafeUtil.getObject(message, offset), UnsafeUtil.getObject(other, offset)); 918 case 50: // MAP: 919 return SchemaUtil.safeEquals( 920 UnsafeUtil.getObject(message, offset), UnsafeUtil.getObject(other, offset)); 921 case 51: // ONEOF_DOUBLE: 922 case 52: // ONEOF_FLOAT: 923 case 53: // ONEOF_INT64: 924 case 54: // ONEOF_UINT64: 925 case 55: // ONEOF_INT32: 926 case 56: // ONEOF_FIXED64: 927 case 57: // ONEOF_FIXED32: 928 case 58: // ONEOF_BOOL: 929 case 59: // ONEOF_STRING: 930 case 60: // ONEOF_MESSAGE: 931 case 61: // ONEOF_BYTES: 932 case 62: // ONEOF_UINT32: 933 case 63: // ONEOF_ENUM: 934 case 64: // ONEOF_SFIXED32: 935 case 65: // ONEOF_SFIXED64: 936 case 66: // ONEOF_SINT32: 937 case 67: // ONEOF_SINT64: 938 case 68: // ONEOF_GROUP: 939 return isOneofCaseEqual(message, other, pos) 940 && SchemaUtil.safeEquals( 941 UnsafeUtil.getObject(message, offset), UnsafeUtil.getObject(other, offset)); 942 default: 943 // Assume it's an empty entry - just go to the next entry. 944 return true; 945 } 946 } 947 948 @Override hashCode(T message)949 public int hashCode(T message) { 950 int hashCode = 0; 951 final int bufferLength = buffer.length; 952 for (int pos = 0; pos < bufferLength; pos += INTS_PER_FIELD) { 953 final int typeAndOffset = typeAndOffsetAt(pos); 954 final int entryNumber = numberAt(pos); 955 956 final long offset = offset(typeAndOffset); 957 958 switch (type(typeAndOffset)) { 959 case 0: // DOUBLE: 960 hashCode = 961 (hashCode * 53) 962 + Internal.hashLong( 963 Double.doubleToLongBits(UnsafeUtil.getDouble(message, offset))); 964 break; 965 case 1: // FLOAT: 966 hashCode = (hashCode * 53) + Float.floatToIntBits(UnsafeUtil.getFloat(message, offset)); 967 break; 968 case 2: // INT64: 969 hashCode = (hashCode * 53) + Internal.hashLong(UnsafeUtil.getLong(message, offset)); 970 break; 971 case 3: // UINT64: 972 hashCode = (hashCode * 53) + Internal.hashLong(UnsafeUtil.getLong(message, offset)); 973 break; 974 case 4: // INT32: 975 hashCode = (hashCode * 53) + (UnsafeUtil.getInt(message, offset)); 976 break; 977 case 5: // FIXED64: 978 hashCode = (hashCode * 53) + Internal.hashLong(UnsafeUtil.getLong(message, offset)); 979 break; 980 case 6: // FIXED32: 981 hashCode = (hashCode * 53) + (UnsafeUtil.getInt(message, offset)); 982 break; 983 case 7: // BOOL: 984 hashCode = (hashCode * 53) + Internal.hashBoolean(UnsafeUtil.getBoolean(message, offset)); 985 break; 986 case 8: // STRING: 987 hashCode = (hashCode * 53) + ((String) UnsafeUtil.getObject(message, offset)).hashCode(); 988 break; 989 case 9: // MESSAGE: 990 { 991 int protoHash = 37; 992 Object submessage = UnsafeUtil.getObject(message, offset); 993 if (submessage != null) { 994 protoHash = submessage.hashCode(); 995 } 996 hashCode = (53 * hashCode) + protoHash; 997 break; 998 } 999 case 10: // BYTES: 1000 hashCode = (hashCode * 53) + UnsafeUtil.getObject(message, offset).hashCode(); 1001 break; 1002 case 11: // UINT32: 1003 hashCode = (hashCode * 53) + (UnsafeUtil.getInt(message, offset)); 1004 break; 1005 case 12: // ENUM: 1006 hashCode = (hashCode * 53) + (UnsafeUtil.getInt(message, offset)); 1007 break; 1008 case 13: // SFIXED32: 1009 hashCode = (hashCode * 53) + (UnsafeUtil.getInt(message, offset)); 1010 break; 1011 case 14: // SFIXED64: 1012 hashCode = (hashCode * 53) + Internal.hashLong(UnsafeUtil.getLong(message, offset)); 1013 break; 1014 case 15: // SINT32: 1015 hashCode = (hashCode * 53) + (UnsafeUtil.getInt(message, offset)); 1016 break; 1017 case 16: // SINT64: 1018 hashCode = (hashCode * 53) + Internal.hashLong(UnsafeUtil.getLong(message, offset)); 1019 break; 1020 1021 case 17: // GROUP: 1022 { 1023 int protoHash = 37; 1024 Object submessage = UnsafeUtil.getObject(message, offset); 1025 if (submessage != null) { 1026 protoHash = submessage.hashCode(); 1027 } 1028 hashCode = (53 * hashCode) + protoHash; 1029 break; 1030 } 1031 case 18: // DOUBLE_LIST: 1032 case 19: // FLOAT_LIST: 1033 case 20: // INT64_LIST: 1034 case 21: // UINT64_LIST: 1035 case 22: // INT32_LIST: 1036 case 23: // FIXED64_LIST: 1037 case 24: // FIXED32_LIST: 1038 case 25: // BOOL_LIST: 1039 case 26: // STRING_LIST: 1040 case 27: // MESSAGE_LIST: 1041 case 28: // BYTES_LIST: 1042 case 29: // UINT32_LIST: 1043 case 30: // ENUM_LIST: 1044 case 31: // SFIXED32_LIST: 1045 case 32: // SFIXED64_LIST: 1046 case 33: // SINT32_LIST: 1047 case 34: // SINT64_LIST: 1048 case 35: // DOUBLE_LIST_PACKED: 1049 case 36: // FLOAT_LIST_PACKED: 1050 case 37: // INT64_LIST_PACKED: 1051 case 38: // UINT64_LIST_PACKED: 1052 case 39: // INT32_LIST_PACKED: 1053 case 40: // FIXED64_LIST_PACKED: 1054 case 41: // FIXED32_LIST_PACKED: 1055 case 42: // BOOL_LIST_PACKED: 1056 case 43: // UINT32_LIST_PACKED: 1057 case 44: // ENUM_LIST_PACKED: 1058 case 45: // SFIXED32_LIST_PACKED: 1059 case 46: // SFIXED64_LIST_PACKED: 1060 case 47: // SINT32_LIST_PACKED: 1061 case 48: // SINT64_LIST_PACKED: 1062 case 49: // GROUP_LIST: 1063 hashCode = (hashCode * 53) + UnsafeUtil.getObject(message, offset).hashCode(); 1064 break; 1065 case 50: // MAP: 1066 hashCode = (hashCode * 53) + UnsafeUtil.getObject(message, offset).hashCode(); 1067 break; 1068 case 51: // ONEOF_DOUBLE: 1069 if (isOneofPresent(message, entryNumber, pos)) { 1070 hashCode = 1071 (hashCode * 53) 1072 + Internal.hashLong(Double.doubleToLongBits(oneofDoubleAt(message, offset))); 1073 } 1074 break; 1075 case 52: // ONEOF_FLOAT: 1076 if (isOneofPresent(message, entryNumber, pos)) { 1077 hashCode = (hashCode * 53) + Float.floatToIntBits(oneofFloatAt(message, offset)); 1078 } 1079 break; 1080 case 53: // ONEOF_INT64: 1081 if (isOneofPresent(message, entryNumber, pos)) { 1082 hashCode = (hashCode * 53) + Internal.hashLong(oneofLongAt(message, offset)); 1083 } 1084 break; 1085 case 54: // ONEOF_UINT64: 1086 if (isOneofPresent(message, entryNumber, pos)) { 1087 hashCode = (hashCode * 53) + Internal.hashLong(oneofLongAt(message, offset)); 1088 } 1089 break; 1090 case 55: // ONEOF_INT32: 1091 if (isOneofPresent(message, entryNumber, pos)) { 1092 hashCode = (hashCode * 53) + (oneofIntAt(message, offset)); 1093 } 1094 break; 1095 case 56: // ONEOF_FIXED64: 1096 if (isOneofPresent(message, entryNumber, pos)) { 1097 hashCode = (hashCode * 53) + Internal.hashLong(oneofLongAt(message, offset)); 1098 } 1099 break; 1100 case 57: // ONEOF_FIXED32: 1101 if (isOneofPresent(message, entryNumber, pos)) { 1102 hashCode = (hashCode * 53) + (oneofIntAt(message, offset)); 1103 } 1104 break; 1105 case 58: // ONEOF_BOOL: 1106 if (isOneofPresent(message, entryNumber, pos)) { 1107 hashCode = (hashCode * 53) + Internal.hashBoolean(oneofBooleanAt(message, offset)); 1108 } 1109 break; 1110 case 59: // ONEOF_STRING: 1111 if (isOneofPresent(message, entryNumber, pos)) { 1112 hashCode = 1113 (hashCode * 53) + ((String) UnsafeUtil.getObject(message, offset)).hashCode(); 1114 } 1115 break; 1116 case 60: // ONEOF_MESSAGE: 1117 if (isOneofPresent(message, entryNumber, pos)) { 1118 Object submessage = UnsafeUtil.getObject(message, offset); 1119 hashCode = (53 * hashCode) + submessage.hashCode(); 1120 } 1121 break; 1122 case 61: // ONEOF_BYTES: 1123 if (isOneofPresent(message, entryNumber, pos)) { 1124 hashCode = (hashCode * 53) + UnsafeUtil.getObject(message, offset).hashCode(); 1125 } 1126 break; 1127 case 62: // ONEOF_UINT32: 1128 if (isOneofPresent(message, entryNumber, pos)) { 1129 hashCode = (hashCode * 53) + (oneofIntAt(message, offset)); 1130 } 1131 break; 1132 case 63: // ONEOF_ENUM: 1133 if (isOneofPresent(message, entryNumber, pos)) { 1134 hashCode = (hashCode * 53) + (oneofIntAt(message, offset)); 1135 } 1136 break; 1137 case 64: // ONEOF_SFIXED32: 1138 if (isOneofPresent(message, entryNumber, pos)) { 1139 hashCode = (hashCode * 53) + (oneofIntAt(message, offset)); 1140 } 1141 break; 1142 case 65: // ONEOF_SFIXED64: 1143 if (isOneofPresent(message, entryNumber, pos)) { 1144 hashCode = (hashCode * 53) + Internal.hashLong(oneofLongAt(message, offset)); 1145 } 1146 break; 1147 case 66: // ONEOF_SINT32: 1148 if (isOneofPresent(message, entryNumber, pos)) { 1149 hashCode = (hashCode * 53) + (oneofIntAt(message, offset)); 1150 } 1151 break; 1152 case 67: // ONEOF_SINT64: 1153 if (isOneofPresent(message, entryNumber, pos)) { 1154 hashCode = (hashCode * 53) + Internal.hashLong(oneofLongAt(message, offset)); 1155 } 1156 break; 1157 case 68: // ONEOF_GROUP: 1158 if (isOneofPresent(message, entryNumber, pos)) { 1159 Object submessage = UnsafeUtil.getObject(message, offset); 1160 hashCode = (53 * hashCode) + submessage.hashCode(); 1161 } 1162 break; 1163 default: 1164 // Assume it's an empty entry - just go to the next entry. 1165 break; 1166 } 1167 } 1168 1169 hashCode = (hashCode * 53) + unknownFieldSchema.getFromMessage(message).hashCode(); 1170 1171 if (hasExtensions) { 1172 hashCode = (hashCode * 53) + extensionSchema.getExtensions(message).hashCode(); 1173 } 1174 1175 return hashCode; 1176 } 1177 1178 @Override mergeFrom(T message, T other)1179 public void mergeFrom(T message, T other) { 1180 checkMutable(message); 1181 if (other == null) { 1182 throw new NullPointerException(); 1183 } 1184 for (int i = 0; i < buffer.length; i += INTS_PER_FIELD) { 1185 // A separate method allows for better JIT optimizations 1186 mergeSingleField(message, other, i); 1187 } 1188 1189 SchemaUtil.mergeUnknownFields(unknownFieldSchema, message, other); 1190 1191 if (hasExtensions) { 1192 SchemaUtil.mergeExtensions(extensionSchema, message, other); 1193 } 1194 } 1195 mergeSingleField(T message, T other, int pos)1196 private void mergeSingleField(T message, T other, int pos) { 1197 final int typeAndOffset = typeAndOffsetAt(pos); 1198 final long offset = offset(typeAndOffset); 1199 final int number = numberAt(pos); 1200 1201 switch (type(typeAndOffset)) { 1202 case 0: // DOUBLE: 1203 if (isFieldPresent(other, pos)) { 1204 UnsafeUtil.putDouble(message, offset, UnsafeUtil.getDouble(other, offset)); 1205 setFieldPresent(message, pos); 1206 } 1207 break; 1208 case 1: // FLOAT: 1209 if (isFieldPresent(other, pos)) { 1210 UnsafeUtil.putFloat(message, offset, UnsafeUtil.getFloat(other, offset)); 1211 setFieldPresent(message, pos); 1212 } 1213 break; 1214 case 2: // INT64: 1215 if (isFieldPresent(other, pos)) { 1216 UnsafeUtil.putLong(message, offset, UnsafeUtil.getLong(other, offset)); 1217 setFieldPresent(message, pos); 1218 } 1219 break; 1220 case 3: // UINT64: 1221 if (isFieldPresent(other, pos)) { 1222 UnsafeUtil.putLong(message, offset, UnsafeUtil.getLong(other, offset)); 1223 setFieldPresent(message, pos); 1224 } 1225 break; 1226 case 4: // INT32: 1227 if (isFieldPresent(other, pos)) { 1228 UnsafeUtil.putInt(message, offset, UnsafeUtil.getInt(other, offset)); 1229 setFieldPresent(message, pos); 1230 } 1231 break; 1232 case 5: // FIXED64: 1233 if (isFieldPresent(other, pos)) { 1234 UnsafeUtil.putLong(message, offset, UnsafeUtil.getLong(other, offset)); 1235 setFieldPresent(message, pos); 1236 } 1237 break; 1238 case 6: // FIXED32: 1239 if (isFieldPresent(other, pos)) { 1240 UnsafeUtil.putInt(message, offset, UnsafeUtil.getInt(other, offset)); 1241 setFieldPresent(message, pos); 1242 } 1243 break; 1244 case 7: // BOOL: 1245 if (isFieldPresent(other, pos)) { 1246 UnsafeUtil.putBoolean(message, offset, UnsafeUtil.getBoolean(other, offset)); 1247 setFieldPresent(message, pos); 1248 } 1249 break; 1250 case 8: // STRING: 1251 if (isFieldPresent(other, pos)) { 1252 UnsafeUtil.putObject(message, offset, UnsafeUtil.getObject(other, offset)); 1253 setFieldPresent(message, pos); 1254 } 1255 break; 1256 case 9: // MESSAGE: 1257 mergeMessage(message, other, pos); 1258 break; 1259 case 10: // BYTES: 1260 if (isFieldPresent(other, pos)) { 1261 UnsafeUtil.putObject(message, offset, UnsafeUtil.getObject(other, offset)); 1262 setFieldPresent(message, pos); 1263 } 1264 break; 1265 case 11: // UINT32: 1266 if (isFieldPresent(other, pos)) { 1267 UnsafeUtil.putInt(message, offset, UnsafeUtil.getInt(other, offset)); 1268 setFieldPresent(message, pos); 1269 } 1270 break; 1271 case 12: // ENUM: 1272 if (isFieldPresent(other, pos)) { 1273 UnsafeUtil.putInt(message, offset, UnsafeUtil.getInt(other, offset)); 1274 setFieldPresent(message, pos); 1275 } 1276 break; 1277 case 13: // SFIXED32: 1278 if (isFieldPresent(other, pos)) { 1279 UnsafeUtil.putInt(message, offset, UnsafeUtil.getInt(other, offset)); 1280 setFieldPresent(message, pos); 1281 } 1282 break; 1283 case 14: // SFIXED64: 1284 if (isFieldPresent(other, pos)) { 1285 UnsafeUtil.putLong(message, offset, UnsafeUtil.getLong(other, offset)); 1286 setFieldPresent(message, pos); 1287 } 1288 break; 1289 case 15: // SINT32: 1290 if (isFieldPresent(other, pos)) { 1291 UnsafeUtil.putInt(message, offset, UnsafeUtil.getInt(other, offset)); 1292 setFieldPresent(message, pos); 1293 } 1294 break; 1295 case 16: // SINT64: 1296 if (isFieldPresent(other, pos)) { 1297 UnsafeUtil.putLong(message, offset, UnsafeUtil.getLong(other, offset)); 1298 setFieldPresent(message, pos); 1299 } 1300 break; 1301 case 17: // GROUP: 1302 mergeMessage(message, other, pos); 1303 break; 1304 case 18: // DOUBLE_LIST: 1305 case 19: // FLOAT_LIST: 1306 case 20: // INT64_LIST: 1307 case 21: // UINT64_LIST: 1308 case 22: // INT32_LIST: 1309 case 23: // FIXED64_LIST: 1310 case 24: // FIXED32_LIST: 1311 case 25: // BOOL_LIST: 1312 case 26: // STRING_LIST: 1313 case 27: // MESSAGE_LIST: 1314 case 28: // BYTES_LIST: 1315 case 29: // UINT32_LIST: 1316 case 30: // ENUM_LIST: 1317 case 31: // SFIXED32_LIST: 1318 case 32: // SFIXED64_LIST: 1319 case 33: // SINT32_LIST: 1320 case 34: // SINT64_LIST: 1321 case 35: // DOUBLE_LIST_PACKED: 1322 case 36: // FLOAT_LIST_PACKED: 1323 case 37: // INT64_LIST_PACKED: 1324 case 38: // UINT64_LIST_PACKED: 1325 case 39: // INT32_LIST_PACKED: 1326 case 40: // FIXED64_LIST_PACKED: 1327 case 41: // FIXED32_LIST_PACKED: 1328 case 42: // BOOL_LIST_PACKED: 1329 case 43: // UINT32_LIST_PACKED: 1330 case 44: // ENUM_LIST_PACKED: 1331 case 45: // SFIXED32_LIST_PACKED: 1332 case 46: // SFIXED64_LIST_PACKED: 1333 case 47: // SINT32_LIST_PACKED: 1334 case 48: // SINT64_LIST_PACKED: 1335 case 49: // GROUP_LIST: 1336 listFieldSchema.mergeListsAt(message, other, offset); 1337 break; 1338 case 50: // MAP: 1339 SchemaUtil.mergeMap(mapFieldSchema, message, other, offset); 1340 break; 1341 case 51: // ONEOF_DOUBLE: 1342 case 52: // ONEOF_FLOAT: 1343 case 53: // ONEOF_INT64: 1344 case 54: // ONEOF_UINT64: 1345 case 55: // ONEOF_INT32: 1346 case 56: // ONEOF_FIXED64: 1347 case 57: // ONEOF_FIXED32: 1348 case 58: // ONEOF_BOOL: 1349 case 59: // ONEOF_STRING: 1350 if (isOneofPresent(other, number, pos)) { 1351 UnsafeUtil.putObject(message, offset, UnsafeUtil.getObject(other, offset)); 1352 setOneofPresent(message, number, pos); 1353 } 1354 break; 1355 1356 case 60: // ONEOF_MESSAGE: 1357 mergeOneofMessage(message, other, pos); 1358 break; 1359 case 61: // ONEOF_BYTES: 1360 case 62: // ONEOF_UINT32: 1361 case 63: // ONEOF_ENUM: 1362 case 64: // ONEOF_SFIXED32: 1363 case 65: // ONEOF_SFIXED64: 1364 case 66: // ONEOF_SINT32: 1365 case 67: // ONEOF_SINT64: 1366 if (isOneofPresent(other, number, pos)) { 1367 UnsafeUtil.putObject(message, offset, UnsafeUtil.getObject(other, offset)); 1368 setOneofPresent(message, number, pos); 1369 } 1370 break; 1371 case 68: // ONEOF_GROUP: 1372 mergeOneofMessage(message, other, pos); 1373 break; 1374 default: 1375 break; 1376 } 1377 } 1378 mergeMessage(T targetParent, T sourceParent, int pos)1379 private void mergeMessage(T targetParent, T sourceParent, int pos) { 1380 if (!isFieldPresent(sourceParent, pos)) { 1381 return; 1382 } 1383 1384 final int typeAndOffset = typeAndOffsetAt(pos); 1385 final long offset = offset(typeAndOffset); 1386 1387 final Object source = UNSAFE.getObject(sourceParent, offset); 1388 if (source == null) { 1389 throw new IllegalStateException( 1390 "Source subfield " + numberAt(pos) + " is present but null: " + sourceParent); 1391 } 1392 1393 final Schema fieldSchema = getMessageFieldSchema(pos); 1394 if (!isFieldPresent(targetParent, pos)) { 1395 if (!isMutable(source)) { 1396 // Can safely share source if it is immutable 1397 UNSAFE.putObject(targetParent, offset, source); 1398 } else { 1399 // Make a safetey copy of source 1400 final Object copyOfSource = fieldSchema.newInstance(); 1401 fieldSchema.mergeFrom(copyOfSource, source); 1402 UNSAFE.putObject(targetParent, offset, copyOfSource); 1403 } 1404 setFieldPresent(targetParent, pos); 1405 return; 1406 } 1407 1408 // Sub-message is present, merge from source 1409 Object target = UNSAFE.getObject(targetParent, offset); 1410 if (!isMutable(target)) { 1411 Object newInstance = fieldSchema.newInstance(); 1412 fieldSchema.mergeFrom(newInstance, target); 1413 UNSAFE.putObject(targetParent, offset, newInstance); 1414 target = newInstance; 1415 } 1416 fieldSchema.mergeFrom(target, source); 1417 } 1418 mergeOneofMessage(T targetParent, T sourceParent, int pos)1419 private void mergeOneofMessage(T targetParent, T sourceParent, int pos) { 1420 int number = numberAt(pos); 1421 if (!isOneofPresent(sourceParent, number, pos)) { 1422 return; 1423 } 1424 1425 long offset = offset(typeAndOffsetAt(pos)); 1426 final Object source = UNSAFE.getObject(sourceParent, offset); 1427 if (source == null) { 1428 throw new IllegalStateException( 1429 "Source subfield " + numberAt(pos) + " is present but null: " + sourceParent); 1430 } 1431 1432 final Schema fieldSchema = getMessageFieldSchema(pos); 1433 if (!isOneofPresent(targetParent, number, pos)) { 1434 if (!isMutable(source)) { 1435 // Can safely share source if it is immutable 1436 UNSAFE.putObject(targetParent, offset, source); 1437 } else { 1438 // Make a safety copy of theirs 1439 final Object copyOfSource = fieldSchema.newInstance(); 1440 fieldSchema.mergeFrom(copyOfSource, source); 1441 UNSAFE.putObject(targetParent, offset, copyOfSource); 1442 } 1443 setOneofPresent(targetParent, number, pos); 1444 return; 1445 } 1446 1447 // Sub-message is present, merge from source 1448 Object target = UNSAFE.getObject(targetParent, offset); 1449 if (!isMutable(target)) { 1450 Object newInstance = fieldSchema.newInstance(); 1451 fieldSchema.mergeFrom(newInstance, target); 1452 UNSAFE.putObject(targetParent, offset, newInstance); 1453 target = newInstance; 1454 } 1455 fieldSchema.mergeFrom(target, source); 1456 } 1457 1458 @Override getSerializedSize(T message)1459 public int getSerializedSize(T message) { 1460 return proto3 ? getSerializedSizeProto3(message) : getSerializedSizeProto2(message); 1461 } 1462 1463 @SuppressWarnings("unchecked") getSerializedSizeProto2(T message)1464 private int getSerializedSizeProto2(T message) { 1465 int size = 0; 1466 1467 final sun.misc.Unsafe unsafe = UNSAFE; 1468 int currentPresenceFieldOffset = NO_PRESENCE_SENTINEL; 1469 int currentPresenceField = 0; 1470 for (int i = 0; i < buffer.length; i += INTS_PER_FIELD) { 1471 final int typeAndOffset = typeAndOffsetAt(i); 1472 final int number = numberAt(i); 1473 1474 int fieldType = type(typeAndOffset); 1475 int presenceMaskAndOffset = 0; 1476 int presenceMask = 0; 1477 if (fieldType <= 17) { 1478 presenceMaskAndOffset = buffer[i + 2]; 1479 final int presenceFieldOffset = presenceMaskAndOffset & OFFSET_MASK; 1480 presenceMask = 1 << (presenceMaskAndOffset >>> OFFSET_BITS); 1481 if (presenceFieldOffset != currentPresenceFieldOffset) { 1482 currentPresenceFieldOffset = presenceFieldOffset; 1483 currentPresenceField = unsafe.getInt(message, (long) presenceFieldOffset); 1484 } 1485 } else if (useCachedSizeField 1486 && fieldType >= FieldType.DOUBLE_LIST_PACKED.id() 1487 && fieldType <= FieldType.SINT64_LIST_PACKED.id()) { 1488 presenceMaskAndOffset = buffer[i + 2] & OFFSET_MASK; 1489 } 1490 1491 final long offset = offset(typeAndOffset); 1492 1493 switch (fieldType) { 1494 case 0: // DOUBLE: 1495 if ((currentPresenceField & presenceMask) != 0) { 1496 size += CodedOutputStream.computeDoubleSize(number, 0); 1497 } 1498 break; 1499 case 1: // FLOAT: 1500 if ((currentPresenceField & presenceMask) != 0) { 1501 size += CodedOutputStream.computeFloatSize(number, 0); 1502 } 1503 break; 1504 case 2: // INT64: 1505 if ((currentPresenceField & presenceMask) != 0) { 1506 size += CodedOutputStream.computeInt64Size(number, unsafe.getLong(message, offset)); 1507 } 1508 break; 1509 case 3: // UINT64: 1510 if ((currentPresenceField & presenceMask) != 0) { 1511 size += CodedOutputStream.computeUInt64Size(number, unsafe.getLong(message, offset)); 1512 } 1513 break; 1514 case 4: // INT32: 1515 if ((currentPresenceField & presenceMask) != 0) { 1516 size += CodedOutputStream.computeInt32Size(number, unsafe.getInt(message, offset)); 1517 } 1518 break; 1519 case 5: // FIXED64: 1520 if ((currentPresenceField & presenceMask) != 0) { 1521 size += CodedOutputStream.computeFixed64Size(number, 0); 1522 } 1523 break; 1524 case 6: // FIXED32: 1525 if ((currentPresenceField & presenceMask) != 0) { 1526 size += CodedOutputStream.computeFixed32Size(number, 0); 1527 } 1528 break; 1529 case 7: // BOOL: 1530 if ((currentPresenceField & presenceMask) != 0) { 1531 size += CodedOutputStream.computeBoolSize(number, true); 1532 } 1533 break; 1534 case 8: // STRING: 1535 if ((currentPresenceField & presenceMask) != 0) { 1536 Object value = unsafe.getObject(message, offset); 1537 if (value instanceof ByteString) { 1538 size += CodedOutputStream.computeBytesSize(number, (ByteString) value); 1539 } else { 1540 size += CodedOutputStream.computeStringSize(number, (String) value); 1541 } 1542 } 1543 break; 1544 case 9: // MESSAGE: 1545 if ((currentPresenceField & presenceMask) != 0) { 1546 Object value = unsafe.getObject(message, offset); 1547 size += SchemaUtil.computeSizeMessage(number, value, getMessageFieldSchema(i)); 1548 } 1549 break; 1550 case 10: // BYTES: 1551 if ((currentPresenceField & presenceMask) != 0) { 1552 ByteString value = (ByteString) unsafe.getObject(message, offset); 1553 size += CodedOutputStream.computeBytesSize(number, value); 1554 } 1555 break; 1556 case 11: // UINT32: 1557 if ((currentPresenceField & presenceMask) != 0) { 1558 size += CodedOutputStream.computeUInt32Size(number, unsafe.getInt(message, offset)); 1559 } 1560 break; 1561 case 12: // ENUM: 1562 if ((currentPresenceField & presenceMask) != 0) { 1563 size += CodedOutputStream.computeEnumSize(number, unsafe.getInt(message, offset)); 1564 } 1565 break; 1566 case 13: // SFIXED32: 1567 if ((currentPresenceField & presenceMask) != 0) { 1568 size += CodedOutputStream.computeSFixed32Size(number, 0); 1569 } 1570 break; 1571 case 14: // SFIXED64: 1572 if ((currentPresenceField & presenceMask) != 0) { 1573 size += CodedOutputStream.computeSFixed64Size(number, 0); 1574 } 1575 break; 1576 case 15: // SINT32: 1577 if ((currentPresenceField & presenceMask) != 0) { 1578 size += CodedOutputStream.computeSInt32Size(number, unsafe.getInt(message, offset)); 1579 } 1580 break; 1581 case 16: // SINT64: 1582 if ((currentPresenceField & presenceMask) != 0) { 1583 size += CodedOutputStream.computeSInt64Size(number, unsafe.getLong(message, offset)); 1584 } 1585 break; 1586 case 17: // GROUP: 1587 if ((currentPresenceField & presenceMask) != 0) { 1588 size += 1589 CodedOutputStream.computeGroupSize( 1590 number, 1591 (MessageLite) unsafe.getObject(message, offset), 1592 getMessageFieldSchema(i)); 1593 } 1594 break; 1595 case 18: // DOUBLE_LIST: 1596 size += 1597 SchemaUtil.computeSizeFixed64List( 1598 number, (List<?>) unsafe.getObject(message, offset), false); 1599 break; 1600 case 19: // FLOAT_LIST: 1601 size += 1602 SchemaUtil.computeSizeFixed32List( 1603 number, (List<?>) unsafe.getObject(message, offset), false); 1604 break; 1605 case 20: // INT64_LIST: 1606 size += 1607 SchemaUtil.computeSizeInt64List( 1608 number, (List<Long>) unsafe.getObject(message, offset), false); 1609 break; 1610 case 21: // UINT64_LIST: 1611 size += 1612 SchemaUtil.computeSizeUInt64List( 1613 number, (List<Long>) unsafe.getObject(message, offset), false); 1614 break; 1615 case 22: // INT32_LIST: 1616 size += 1617 SchemaUtil.computeSizeInt32List( 1618 number, (List<Integer>) unsafe.getObject(message, offset), false); 1619 break; 1620 case 23: // FIXED64_LIST: 1621 size += 1622 SchemaUtil.computeSizeFixed64List( 1623 number, (List<?>) unsafe.getObject(message, offset), false); 1624 break; 1625 case 24: // FIXED32_LIST: 1626 size += 1627 SchemaUtil.computeSizeFixed32List( 1628 number, (List<?>) unsafe.getObject(message, offset), false); 1629 break; 1630 case 25: // BOOL_LIST: 1631 size += 1632 SchemaUtil.computeSizeBoolList( 1633 number, (List<?>) unsafe.getObject(message, offset), false); 1634 break; 1635 case 26: // STRING_LIST: 1636 size += 1637 SchemaUtil.computeSizeStringList(number, (List<?>) unsafe.getObject(message, offset)); 1638 break; 1639 case 27: // MESSAGE_LIST: 1640 size += 1641 SchemaUtil.computeSizeMessageList( 1642 number, (List<?>) unsafe.getObject(message, offset), getMessageFieldSchema(i)); 1643 break; 1644 case 28: // BYTES_LIST: 1645 size += 1646 SchemaUtil.computeSizeByteStringList( 1647 number, (List<ByteString>) unsafe.getObject(message, offset)); 1648 break; 1649 case 29: // UINT32_LIST: 1650 size += 1651 SchemaUtil.computeSizeUInt32List( 1652 number, (List<Integer>) unsafe.getObject(message, offset), false); 1653 break; 1654 case 30: // ENUM_LIST: 1655 size += 1656 SchemaUtil.computeSizeEnumList( 1657 number, (List<Integer>) unsafe.getObject(message, offset), false); 1658 break; 1659 case 31: // SFIXED32_LIST: 1660 size += 1661 SchemaUtil.computeSizeFixed32List( 1662 number, (List<Integer>) unsafe.getObject(message, offset), false); 1663 break; 1664 case 32: // SFIXED64_LIST: 1665 size += 1666 SchemaUtil.computeSizeFixed64List( 1667 number, (List<Long>) unsafe.getObject(message, offset), false); 1668 break; 1669 case 33: // SINT32_LIST: 1670 size += 1671 SchemaUtil.computeSizeSInt32List( 1672 number, (List<Integer>) unsafe.getObject(message, offset), false); 1673 break; 1674 case 34: // SINT64_LIST: 1675 size += 1676 SchemaUtil.computeSizeSInt64List( 1677 number, (List<Long>) unsafe.getObject(message, offset), false); 1678 break; 1679 case 35: 1680 { // DOUBLE_LIST_PACKED: 1681 int fieldSize = 1682 SchemaUtil.computeSizeFixed64ListNoTag( 1683 (List<Double>) unsafe.getObject(message, offset)); 1684 if (fieldSize > 0) { 1685 if (useCachedSizeField) { 1686 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1687 } 1688 size += 1689 CodedOutputStream.computeTagSize(number) 1690 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1691 + fieldSize; 1692 } 1693 break; 1694 } 1695 case 36: 1696 { // FLOAT_LIST_PACKED: 1697 int fieldSize = 1698 SchemaUtil.computeSizeFixed32ListNoTag( 1699 (List<Float>) unsafe.getObject(message, offset)); 1700 if (fieldSize > 0) { 1701 if (useCachedSizeField) { 1702 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1703 } 1704 size += 1705 CodedOutputStream.computeTagSize(number) 1706 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1707 + fieldSize; 1708 } 1709 break; 1710 } 1711 case 37: 1712 { // INT64_LIST_PACKED: 1713 int fieldSize = 1714 SchemaUtil.computeSizeInt64ListNoTag( 1715 (List<Long>) unsafe.getObject(message, offset)); 1716 if (fieldSize > 0) { 1717 if (useCachedSizeField) { 1718 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1719 } 1720 size += 1721 CodedOutputStream.computeTagSize(number) 1722 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1723 + fieldSize; 1724 } 1725 break; 1726 } 1727 case 38: 1728 { // UINT64_LIST_PACKED: 1729 int fieldSize = 1730 SchemaUtil.computeSizeUInt64ListNoTag( 1731 (List<Long>) unsafe.getObject(message, offset)); 1732 if (fieldSize > 0) { 1733 if (useCachedSizeField) { 1734 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1735 } 1736 size += 1737 CodedOutputStream.computeTagSize(number) 1738 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1739 + fieldSize; 1740 } 1741 break; 1742 } 1743 case 39: 1744 { // INT32_LIST_PACKED: 1745 int fieldSize = 1746 SchemaUtil.computeSizeInt32ListNoTag( 1747 (List<Integer>) unsafe.getObject(message, offset)); 1748 if (fieldSize > 0) { 1749 if (useCachedSizeField) { 1750 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1751 } 1752 size += 1753 CodedOutputStream.computeTagSize(number) 1754 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1755 + fieldSize; 1756 } 1757 break; 1758 } 1759 case 40: 1760 { // FIXED64_LIST_PACKED: 1761 int fieldSize = 1762 SchemaUtil.computeSizeFixed64ListNoTag( 1763 (List<Long>) unsafe.getObject(message, offset)); 1764 if (fieldSize > 0) { 1765 if (useCachedSizeField) { 1766 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1767 } 1768 size += 1769 CodedOutputStream.computeTagSize(number) 1770 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1771 + fieldSize; 1772 } 1773 break; 1774 } 1775 case 41: 1776 { // FIXED32_LIST_PACKED: 1777 int fieldSize = 1778 SchemaUtil.computeSizeFixed32ListNoTag( 1779 (List<Integer>) unsafe.getObject(message, offset)); 1780 if (fieldSize > 0) { 1781 if (useCachedSizeField) { 1782 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1783 } 1784 size += 1785 CodedOutputStream.computeTagSize(number) 1786 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1787 + fieldSize; 1788 } 1789 break; 1790 } 1791 case 42: 1792 { // BOOL_LIST_PACKED: 1793 int fieldSize = 1794 SchemaUtil.computeSizeBoolListNoTag( 1795 (List<Boolean>) unsafe.getObject(message, offset)); 1796 if (fieldSize > 0) { 1797 if (useCachedSizeField) { 1798 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1799 } 1800 size += 1801 CodedOutputStream.computeTagSize(number) 1802 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1803 + fieldSize; 1804 } 1805 break; 1806 } 1807 case 43: 1808 { // UINT32_LIST_PACKED: 1809 int fieldSize = 1810 SchemaUtil.computeSizeUInt32ListNoTag( 1811 (List<Integer>) unsafe.getObject(message, offset)); 1812 if (fieldSize > 0) { 1813 if (useCachedSizeField) { 1814 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1815 } 1816 size += 1817 CodedOutputStream.computeTagSize(number) 1818 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1819 + fieldSize; 1820 } 1821 break; 1822 } 1823 case 44: 1824 { // ENUM_LIST_PACKED: 1825 int fieldSize = 1826 SchemaUtil.computeSizeEnumListNoTag( 1827 (List<Integer>) unsafe.getObject(message, offset)); 1828 if (fieldSize > 0) { 1829 if (useCachedSizeField) { 1830 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1831 } 1832 size += 1833 CodedOutputStream.computeTagSize(number) 1834 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1835 + fieldSize; 1836 } 1837 break; 1838 } 1839 case 45: 1840 { // SFIXED32_LIST_PACKED: 1841 int fieldSize = 1842 SchemaUtil.computeSizeFixed32ListNoTag( 1843 (List<Integer>) unsafe.getObject(message, offset)); 1844 if (fieldSize > 0) { 1845 if (useCachedSizeField) { 1846 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1847 } 1848 size += 1849 CodedOutputStream.computeTagSize(number) 1850 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1851 + fieldSize; 1852 } 1853 break; 1854 } 1855 case 46: 1856 { // SFIXED64_LIST_PACKED: 1857 int fieldSize = 1858 SchemaUtil.computeSizeFixed64ListNoTag( 1859 (List<Long>) unsafe.getObject(message, offset)); 1860 if (fieldSize > 0) { 1861 if (useCachedSizeField) { 1862 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1863 } 1864 size += 1865 CodedOutputStream.computeTagSize(number) 1866 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1867 + fieldSize; 1868 } 1869 break; 1870 } 1871 case 47: 1872 { // SINT32_LIST_PACKED: 1873 int fieldSize = 1874 SchemaUtil.computeSizeSInt32ListNoTag( 1875 (List<Integer>) unsafe.getObject(message, offset)); 1876 if (fieldSize > 0) { 1877 if (useCachedSizeField) { 1878 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1879 } 1880 size += 1881 CodedOutputStream.computeTagSize(number) 1882 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1883 + fieldSize; 1884 } 1885 break; 1886 } 1887 case 48: 1888 { // SINT64_LIST_PACKED: 1889 int fieldSize = 1890 SchemaUtil.computeSizeSInt64ListNoTag( 1891 (List<Long>) unsafe.getObject(message, offset)); 1892 if (fieldSize > 0) { 1893 if (useCachedSizeField) { 1894 unsafe.putInt(message, (long) presenceMaskAndOffset, fieldSize); 1895 } 1896 size += 1897 CodedOutputStream.computeTagSize(number) 1898 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 1899 + fieldSize; 1900 } 1901 break; 1902 } 1903 case 49: // GROUP_LIST: 1904 size += 1905 SchemaUtil.computeSizeGroupList( 1906 number, 1907 (List<MessageLite>) unsafe.getObject(message, offset), 1908 getMessageFieldSchema(i)); 1909 break; 1910 case 50: // MAP: 1911 // TODO(dweis): Use schema cache. 1912 size += 1913 mapFieldSchema.getSerializedSize( 1914 number, unsafe.getObject(message, offset), getMapFieldDefaultEntry(i)); 1915 break; 1916 case 51: // ONEOF_DOUBLE: 1917 if (isOneofPresent(message, number, i)) { 1918 size += CodedOutputStream.computeDoubleSize(number, 0); 1919 } 1920 break; 1921 case 52: // ONEOF_FLOAT: 1922 if (isOneofPresent(message, number, i)) { 1923 size += CodedOutputStream.computeFloatSize(number, 0); 1924 } 1925 break; 1926 case 53: // ONEOF_INT64: 1927 if (isOneofPresent(message, number, i)) { 1928 size += CodedOutputStream.computeInt64Size(number, oneofLongAt(message, offset)); 1929 } 1930 break; 1931 case 54: // ONEOF_UINT64: 1932 if (isOneofPresent(message, number, i)) { 1933 size += CodedOutputStream.computeUInt64Size(number, oneofLongAt(message, offset)); 1934 } 1935 break; 1936 case 55: // ONEOF_INT32: 1937 if (isOneofPresent(message, number, i)) { 1938 size += CodedOutputStream.computeInt32Size(number, oneofIntAt(message, offset)); 1939 } 1940 break; 1941 case 56: // ONEOF_FIXED64: 1942 if (isOneofPresent(message, number, i)) { 1943 size += CodedOutputStream.computeFixed64Size(number, 0); 1944 } 1945 break; 1946 case 57: // ONEOF_FIXED32: 1947 if (isOneofPresent(message, number, i)) { 1948 size += CodedOutputStream.computeFixed32Size(number, 0); 1949 } 1950 break; 1951 case 58: // ONEOF_BOOL: 1952 if (isOneofPresent(message, number, i)) { 1953 size += CodedOutputStream.computeBoolSize(number, true); 1954 } 1955 break; 1956 case 59: // ONEOF_STRING: 1957 if (isOneofPresent(message, number, i)) { 1958 Object value = unsafe.getObject(message, offset); 1959 if (value instanceof ByteString) { 1960 size += CodedOutputStream.computeBytesSize(number, (ByteString) value); 1961 } else { 1962 size += CodedOutputStream.computeStringSize(number, (String) value); 1963 } 1964 } 1965 break; 1966 case 60: // ONEOF_MESSAGE: 1967 if (isOneofPresent(message, number, i)) { 1968 Object value = unsafe.getObject(message, offset); 1969 size += SchemaUtil.computeSizeMessage(number, value, getMessageFieldSchema(i)); 1970 } 1971 break; 1972 case 61: // ONEOF_BYTES: 1973 if (isOneofPresent(message, number, i)) { 1974 size += 1975 CodedOutputStream.computeBytesSize( 1976 number, (ByteString) unsafe.getObject(message, offset)); 1977 } 1978 break; 1979 case 62: // ONEOF_UINT32: 1980 if (isOneofPresent(message, number, i)) { 1981 size += CodedOutputStream.computeUInt32Size(number, oneofIntAt(message, offset)); 1982 } 1983 break; 1984 case 63: // ONEOF_ENUM: 1985 if (isOneofPresent(message, number, i)) { 1986 size += CodedOutputStream.computeEnumSize(number, oneofIntAt(message, offset)); 1987 } 1988 break; 1989 case 64: // ONEOF_SFIXED32: 1990 if (isOneofPresent(message, number, i)) { 1991 size += CodedOutputStream.computeSFixed32Size(number, 0); 1992 } 1993 break; 1994 case 65: // ONEOF_SFIXED64: 1995 if (isOneofPresent(message, number, i)) { 1996 size += CodedOutputStream.computeSFixed64Size(number, 0); 1997 } 1998 break; 1999 case 66: // ONEOF_SINT32: 2000 if (isOneofPresent(message, number, i)) { 2001 size += CodedOutputStream.computeSInt32Size(number, oneofIntAt(message, offset)); 2002 } 2003 break; 2004 case 67: // ONEOF_SINT64: 2005 if (isOneofPresent(message, number, i)) { 2006 size += CodedOutputStream.computeSInt64Size(number, oneofLongAt(message, offset)); 2007 } 2008 break; 2009 case 68: // ONEOF_GROUP: 2010 if (isOneofPresent(message, number, i)) { 2011 size += 2012 CodedOutputStream.computeGroupSize( 2013 number, 2014 (MessageLite) unsafe.getObject(message, offset), 2015 getMessageFieldSchema(i)); 2016 } 2017 break; 2018 default: 2019 // Assume it's an empty entry. 2020 } 2021 } 2022 2023 size += getUnknownFieldsSerializedSize(unknownFieldSchema, message); 2024 2025 if (hasExtensions) { 2026 size += extensionSchema.getExtensions(message).getSerializedSize(); 2027 } 2028 2029 return size; 2030 } 2031 getSerializedSizeProto3(T message)2032 private int getSerializedSizeProto3(T message) { 2033 final sun.misc.Unsafe unsafe = UNSAFE; 2034 int size = 0; 2035 for (int i = 0; i < buffer.length; i += INTS_PER_FIELD) { 2036 final int typeAndOffset = typeAndOffsetAt(i); 2037 final int fieldType = type(typeAndOffset); 2038 final int number = numberAt(i); 2039 2040 final long offset = offset(typeAndOffset); 2041 final int cachedSizeOffset = 2042 fieldType >= FieldType.DOUBLE_LIST_PACKED.id() 2043 && fieldType <= FieldType.SINT64_LIST_PACKED.id() 2044 ? buffer[i + 2] & OFFSET_MASK 2045 : 0; 2046 2047 switch (fieldType) { 2048 case 0: // DOUBLE: 2049 if (isFieldPresent(message, i)) { 2050 size += CodedOutputStream.computeDoubleSize(number, 0); 2051 } 2052 break; 2053 case 1: // FLOAT: 2054 if (isFieldPresent(message, i)) { 2055 size += CodedOutputStream.computeFloatSize(number, 0); 2056 } 2057 break; 2058 case 2: // INT64: 2059 if (isFieldPresent(message, i)) { 2060 size += CodedOutputStream.computeInt64Size(number, UnsafeUtil.getLong(message, offset)); 2061 } 2062 break; 2063 case 3: // UINT64: 2064 if (isFieldPresent(message, i)) { 2065 size += 2066 CodedOutputStream.computeUInt64Size(number, UnsafeUtil.getLong(message, offset)); 2067 } 2068 break; 2069 case 4: // INT32: 2070 if (isFieldPresent(message, i)) { 2071 size += CodedOutputStream.computeInt32Size(number, UnsafeUtil.getInt(message, offset)); 2072 } 2073 break; 2074 case 5: // FIXED64: 2075 if (isFieldPresent(message, i)) { 2076 size += CodedOutputStream.computeFixed64Size(number, 0); 2077 } 2078 break; 2079 case 6: // FIXED32: 2080 if (isFieldPresent(message, i)) { 2081 size += CodedOutputStream.computeFixed32Size(number, 0); 2082 } 2083 break; 2084 case 7: // BOOL: 2085 if (isFieldPresent(message, i)) { 2086 size += CodedOutputStream.computeBoolSize(number, true); 2087 } 2088 break; 2089 case 8: // STRING: 2090 if (isFieldPresent(message, i)) { 2091 Object value = UnsafeUtil.getObject(message, offset); 2092 if (value instanceof ByteString) { 2093 size += CodedOutputStream.computeBytesSize(number, (ByteString) value); 2094 } else { 2095 size += CodedOutputStream.computeStringSize(number, (String) value); 2096 } 2097 } 2098 break; 2099 case 9: // MESSAGE: 2100 if (isFieldPresent(message, i)) { 2101 Object value = UnsafeUtil.getObject(message, offset); 2102 size += SchemaUtil.computeSizeMessage(number, value, getMessageFieldSchema(i)); 2103 } 2104 break; 2105 case 10: // BYTES: 2106 if (isFieldPresent(message, i)) { 2107 ByteString value = (ByteString) UnsafeUtil.getObject(message, offset); 2108 size += CodedOutputStream.computeBytesSize(number, value); 2109 } 2110 break; 2111 case 11: // UINT32: 2112 if (isFieldPresent(message, i)) { 2113 size += CodedOutputStream.computeUInt32Size(number, UnsafeUtil.getInt(message, offset)); 2114 } 2115 break; 2116 case 12: // ENUM: 2117 if (isFieldPresent(message, i)) { 2118 size += CodedOutputStream.computeEnumSize(number, UnsafeUtil.getInt(message, offset)); 2119 } 2120 break; 2121 case 13: // SFIXED32: 2122 if (isFieldPresent(message, i)) { 2123 size += CodedOutputStream.computeSFixed32Size(number, 0); 2124 } 2125 break; 2126 case 14: // SFIXED64: 2127 if (isFieldPresent(message, i)) { 2128 size += CodedOutputStream.computeSFixed64Size(number, 0); 2129 } 2130 break; 2131 case 15: // SINT32: 2132 if (isFieldPresent(message, i)) { 2133 size += CodedOutputStream.computeSInt32Size(number, UnsafeUtil.getInt(message, offset)); 2134 } 2135 break; 2136 case 16: // SINT64: 2137 if (isFieldPresent(message, i)) { 2138 size += 2139 CodedOutputStream.computeSInt64Size(number, UnsafeUtil.getLong(message, offset)); 2140 } 2141 break; 2142 case 17: // GROUP: 2143 if (isFieldPresent(message, i)) { 2144 size += 2145 CodedOutputStream.computeGroupSize( 2146 number, 2147 (MessageLite) UnsafeUtil.getObject(message, offset), 2148 getMessageFieldSchema(i)); 2149 } 2150 break; 2151 case 18: // DOUBLE_LIST: 2152 size += SchemaUtil.computeSizeFixed64List(number, listAt(message, offset), false); 2153 break; 2154 case 19: // FLOAT_LIST: 2155 size += SchemaUtil.computeSizeFixed32List(number, listAt(message, offset), false); 2156 break; 2157 case 20: // INT64_LIST: 2158 size += 2159 SchemaUtil.computeSizeInt64List(number, (List<Long>) listAt(message, offset), false); 2160 break; 2161 case 21: // UINT64_LIST: 2162 size += 2163 SchemaUtil.computeSizeUInt64List(number, (List<Long>) listAt(message, offset), false); 2164 break; 2165 case 22: // INT32_LIST: 2166 size += 2167 SchemaUtil.computeSizeInt32List( 2168 number, (List<Integer>) listAt(message, offset), false); 2169 break; 2170 case 23: // FIXED64_LIST: 2171 size += SchemaUtil.computeSizeFixed64List(number, listAt(message, offset), false); 2172 break; 2173 case 24: // FIXED32_LIST: 2174 size += SchemaUtil.computeSizeFixed32List(number, listAt(message, offset), false); 2175 break; 2176 case 25: // BOOL_LIST: 2177 size += SchemaUtil.computeSizeBoolList(number, listAt(message, offset), false); 2178 break; 2179 case 26: // STRING_LIST: 2180 size += SchemaUtil.computeSizeStringList(number, listAt(message, offset)); 2181 break; 2182 case 27: // MESSAGE_LIST: 2183 size += 2184 SchemaUtil.computeSizeMessageList( 2185 number, listAt(message, offset), getMessageFieldSchema(i)); 2186 break; 2187 case 28: // BYTES_LIST: 2188 size += 2189 SchemaUtil.computeSizeByteStringList( 2190 number, (List<ByteString>) listAt(message, offset)); 2191 break; 2192 case 29: // UINT32_LIST: 2193 size += 2194 SchemaUtil.computeSizeUInt32List( 2195 number, (List<Integer>) listAt(message, offset), false); 2196 break; 2197 case 30: // ENUM_LIST: 2198 size += 2199 SchemaUtil.computeSizeEnumList( 2200 number, (List<Integer>) listAt(message, offset), false); 2201 break; 2202 case 31: // SFIXED32_LIST: 2203 size += SchemaUtil.computeSizeFixed32List(number, listAt(message, offset), false); 2204 break; 2205 case 32: // SFIXED64_LIST: 2206 size += SchemaUtil.computeSizeFixed64List(number, listAt(message, offset), false); 2207 break; 2208 case 33: // SINT32_LIST: 2209 size += 2210 SchemaUtil.computeSizeSInt32List( 2211 number, (List<Integer>) listAt(message, offset), false); 2212 break; 2213 case 34: // SINT64_LIST: 2214 size += 2215 SchemaUtil.computeSizeSInt64List(number, (List<Long>) listAt(message, offset), false); 2216 break; 2217 case 35: 2218 { // DOUBLE_LIST_PACKED: 2219 int fieldSize = 2220 SchemaUtil.computeSizeFixed64ListNoTag( 2221 (List<Double>) unsafe.getObject(message, offset)); 2222 if (fieldSize > 0) { 2223 if (useCachedSizeField) { 2224 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2225 } 2226 size += 2227 CodedOutputStream.computeTagSize(number) 2228 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2229 + fieldSize; 2230 } 2231 break; 2232 } 2233 case 36: 2234 { // FLOAT_LIST_PACKED: 2235 int fieldSize = 2236 SchemaUtil.computeSizeFixed32ListNoTag( 2237 (List<Float>) unsafe.getObject(message, offset)); 2238 if (fieldSize > 0) { 2239 if (useCachedSizeField) { 2240 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2241 } 2242 size += 2243 CodedOutputStream.computeTagSize(number) 2244 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2245 + fieldSize; 2246 } 2247 break; 2248 } 2249 case 37: 2250 { // INT64_LIST_PACKED: 2251 int fieldSize = 2252 SchemaUtil.computeSizeInt64ListNoTag( 2253 (List<Long>) unsafe.getObject(message, offset)); 2254 if (fieldSize > 0) { 2255 if (useCachedSizeField) { 2256 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2257 } 2258 size += 2259 CodedOutputStream.computeTagSize(number) 2260 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2261 + fieldSize; 2262 } 2263 break; 2264 } 2265 case 38: 2266 { // UINT64_LIST_PACKED: 2267 int fieldSize = 2268 SchemaUtil.computeSizeUInt64ListNoTag( 2269 (List<Long>) unsafe.getObject(message, offset)); 2270 if (fieldSize > 0) { 2271 if (useCachedSizeField) { 2272 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2273 } 2274 size += 2275 CodedOutputStream.computeTagSize(number) 2276 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2277 + fieldSize; 2278 } 2279 break; 2280 } 2281 case 39: 2282 { // INT32_LIST_PACKED: 2283 int fieldSize = 2284 SchemaUtil.computeSizeInt32ListNoTag( 2285 (List<Integer>) unsafe.getObject(message, offset)); 2286 if (fieldSize > 0) { 2287 if (useCachedSizeField) { 2288 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2289 } 2290 size += 2291 CodedOutputStream.computeTagSize(number) 2292 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2293 + fieldSize; 2294 } 2295 break; 2296 } 2297 case 40: 2298 { // FIXED64_LIST_PACKED: 2299 int fieldSize = 2300 SchemaUtil.computeSizeFixed64ListNoTag( 2301 (List<Long>) unsafe.getObject(message, offset)); 2302 if (fieldSize > 0) { 2303 if (useCachedSizeField) { 2304 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2305 } 2306 size += 2307 CodedOutputStream.computeTagSize(number) 2308 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2309 + fieldSize; 2310 } 2311 break; 2312 } 2313 case 41: 2314 { // FIXED32_LIST_PACKED: 2315 int fieldSize = 2316 SchemaUtil.computeSizeFixed32ListNoTag( 2317 (List<Integer>) unsafe.getObject(message, offset)); 2318 if (fieldSize > 0) { 2319 if (useCachedSizeField) { 2320 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2321 } 2322 size += 2323 CodedOutputStream.computeTagSize(number) 2324 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2325 + fieldSize; 2326 } 2327 break; 2328 } 2329 case 42: 2330 { // BOOL_LIST_PACKED: 2331 int fieldSize = 2332 SchemaUtil.computeSizeBoolListNoTag( 2333 (List<Boolean>) unsafe.getObject(message, offset)); 2334 if (fieldSize > 0) { 2335 if (useCachedSizeField) { 2336 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2337 } 2338 size += 2339 CodedOutputStream.computeTagSize(number) 2340 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2341 + fieldSize; 2342 } 2343 break; 2344 } 2345 case 43: 2346 { // UINT32_LIST_PACKED: 2347 int fieldSize = 2348 SchemaUtil.computeSizeUInt32ListNoTag( 2349 (List<Integer>) unsafe.getObject(message, offset)); 2350 if (fieldSize > 0) { 2351 if (useCachedSizeField) { 2352 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2353 } 2354 size += 2355 CodedOutputStream.computeTagSize(number) 2356 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2357 + fieldSize; 2358 } 2359 break; 2360 } 2361 case 44: 2362 { // ENUM_LIST_PACKED: 2363 int fieldSize = 2364 SchemaUtil.computeSizeEnumListNoTag( 2365 (List<Integer>) unsafe.getObject(message, offset)); 2366 if (fieldSize > 0) { 2367 if (useCachedSizeField) { 2368 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2369 } 2370 size += 2371 CodedOutputStream.computeTagSize(number) 2372 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2373 + fieldSize; 2374 } 2375 break; 2376 } 2377 case 45: 2378 { // SFIXED32_LIST_PACKED: 2379 int fieldSize = 2380 SchemaUtil.computeSizeFixed32ListNoTag( 2381 (List<Integer>) unsafe.getObject(message, offset)); 2382 if (fieldSize > 0) { 2383 if (useCachedSizeField) { 2384 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2385 } 2386 size += 2387 CodedOutputStream.computeTagSize(number) 2388 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2389 + fieldSize; 2390 } 2391 break; 2392 } 2393 case 46: 2394 { // SFIXED64_LIST_PACKED: 2395 int fieldSize = 2396 SchemaUtil.computeSizeFixed64ListNoTag( 2397 (List<Long>) unsafe.getObject(message, offset)); 2398 if (fieldSize > 0) { 2399 if (useCachedSizeField) { 2400 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2401 } 2402 size += 2403 CodedOutputStream.computeTagSize(number) 2404 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2405 + fieldSize; 2406 } 2407 break; 2408 } 2409 case 47: 2410 { // SINT32_LIST_PACKED: 2411 int fieldSize = 2412 SchemaUtil.computeSizeSInt32ListNoTag( 2413 (List<Integer>) unsafe.getObject(message, offset)); 2414 if (fieldSize > 0) { 2415 if (useCachedSizeField) { 2416 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2417 } 2418 size += 2419 CodedOutputStream.computeTagSize(number) 2420 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2421 + fieldSize; 2422 } 2423 break; 2424 } 2425 case 48: 2426 { // SINT64_LIST_PACKED: 2427 int fieldSize = 2428 SchemaUtil.computeSizeSInt64ListNoTag( 2429 (List<Long>) unsafe.getObject(message, offset)); 2430 if (fieldSize > 0) { 2431 if (useCachedSizeField) { 2432 unsafe.putInt(message, (long) cachedSizeOffset, fieldSize); 2433 } 2434 size += 2435 CodedOutputStream.computeTagSize(number) 2436 + CodedOutputStream.computeUInt32SizeNoTag(fieldSize) 2437 + fieldSize; 2438 } 2439 break; 2440 } 2441 case 49: // GROUP_LIST: 2442 size += 2443 SchemaUtil.computeSizeGroupList( 2444 number, (List<MessageLite>) listAt(message, offset), getMessageFieldSchema(i)); 2445 break; 2446 case 50: // MAP: 2447 // TODO(dweis): Use schema cache. 2448 size += 2449 mapFieldSchema.getSerializedSize( 2450 number, UnsafeUtil.getObject(message, offset), getMapFieldDefaultEntry(i)); 2451 break; 2452 case 51: // ONEOF_DOUBLE: 2453 if (isOneofPresent(message, number, i)) { 2454 size += CodedOutputStream.computeDoubleSize(number, 0); 2455 } 2456 break; 2457 case 52: // ONEOF_FLOAT: 2458 if (isOneofPresent(message, number, i)) { 2459 size += CodedOutputStream.computeFloatSize(number, 0); 2460 } 2461 break; 2462 case 53: // ONEOF_INT64: 2463 if (isOneofPresent(message, number, i)) { 2464 size += CodedOutputStream.computeInt64Size(number, oneofLongAt(message, offset)); 2465 } 2466 break; 2467 case 54: // ONEOF_UINT64: 2468 if (isOneofPresent(message, number, i)) { 2469 size += CodedOutputStream.computeUInt64Size(number, oneofLongAt(message, offset)); 2470 } 2471 break; 2472 case 55: // ONEOF_INT32: 2473 if (isOneofPresent(message, number, i)) { 2474 size += CodedOutputStream.computeInt32Size(number, oneofIntAt(message, offset)); 2475 } 2476 break; 2477 case 56: // ONEOF_FIXED64: 2478 if (isOneofPresent(message, number, i)) { 2479 size += CodedOutputStream.computeFixed64Size(number, 0); 2480 } 2481 break; 2482 case 57: // ONEOF_FIXED32: 2483 if (isOneofPresent(message, number, i)) { 2484 size += CodedOutputStream.computeFixed32Size(number, 0); 2485 } 2486 break; 2487 case 58: // ONEOF_BOOL: 2488 if (isOneofPresent(message, number, i)) { 2489 size += CodedOutputStream.computeBoolSize(number, true); 2490 } 2491 break; 2492 case 59: // ONEOF_STRING: 2493 if (isOneofPresent(message, number, i)) { 2494 Object value = UnsafeUtil.getObject(message, offset); 2495 if (value instanceof ByteString) { 2496 size += CodedOutputStream.computeBytesSize(number, (ByteString) value); 2497 } else { 2498 size += CodedOutputStream.computeStringSize(number, (String) value); 2499 } 2500 } 2501 break; 2502 case 60: // ONEOF_MESSAGE: 2503 if (isOneofPresent(message, number, i)) { 2504 Object value = UnsafeUtil.getObject(message, offset); 2505 size += SchemaUtil.computeSizeMessage(number, value, getMessageFieldSchema(i)); 2506 } 2507 break; 2508 case 61: // ONEOF_BYTES: 2509 if (isOneofPresent(message, number, i)) { 2510 size += 2511 CodedOutputStream.computeBytesSize( 2512 number, (ByteString) UnsafeUtil.getObject(message, offset)); 2513 } 2514 break; 2515 case 62: // ONEOF_UINT32: 2516 if (isOneofPresent(message, number, i)) { 2517 size += CodedOutputStream.computeUInt32Size(number, oneofIntAt(message, offset)); 2518 } 2519 break; 2520 case 63: // ONEOF_ENUM: 2521 if (isOneofPresent(message, number, i)) { 2522 size += CodedOutputStream.computeEnumSize(number, oneofIntAt(message, offset)); 2523 } 2524 break; 2525 case 64: // ONEOF_SFIXED32: 2526 if (isOneofPresent(message, number, i)) { 2527 size += CodedOutputStream.computeSFixed32Size(number, 0); 2528 } 2529 break; 2530 case 65: // ONEOF_SFIXED64: 2531 if (isOneofPresent(message, number, i)) { 2532 size += CodedOutputStream.computeSFixed64Size(number, 0); 2533 } 2534 break; 2535 case 66: // ONEOF_SINT32: 2536 if (isOneofPresent(message, number, i)) { 2537 size += CodedOutputStream.computeSInt32Size(number, oneofIntAt(message, offset)); 2538 } 2539 break; 2540 case 67: // ONEOF_SINT64: 2541 if (isOneofPresent(message, number, i)) { 2542 size += CodedOutputStream.computeSInt64Size(number, oneofLongAt(message, offset)); 2543 } 2544 break; 2545 case 68: // ONEOF_GROUP: 2546 if (isOneofPresent(message, number, i)) { 2547 size += 2548 CodedOutputStream.computeGroupSize( 2549 number, 2550 (MessageLite) UnsafeUtil.getObject(message, offset), 2551 getMessageFieldSchema(i)); 2552 } 2553 break; 2554 default: 2555 // Assume it's an empty entry. 2556 } 2557 } 2558 2559 size += getUnknownFieldsSerializedSize(unknownFieldSchema, message); 2560 2561 return size; 2562 } 2563 getUnknownFieldsSerializedSize( UnknownFieldSchema<UT, UB> schema, T message)2564 private <UT, UB> int getUnknownFieldsSerializedSize( 2565 UnknownFieldSchema<UT, UB> schema, T message) { 2566 UT unknowns = schema.getFromMessage(message); 2567 return schema.getSerializedSize(unknowns); 2568 } 2569 listAt(Object message, long offset)2570 private static List<?> listAt(Object message, long offset) { 2571 return (List<?>) UnsafeUtil.getObject(message, offset); 2572 } 2573 2574 @SuppressWarnings("unchecked") 2575 @Override 2576 // TODO(nathanmittler): Consider serializing oneof fields last so that only one entry per 2577 // oneof is actually serialized. This would mean that we would violate the serialization order 2578 // contract. It should also be noted that Go currently does this. writeTo(T message, Writer writer)2579 public void writeTo(T message, Writer writer) throws IOException { 2580 if (writer.fieldOrder() == Writer.FieldOrder.DESCENDING) { 2581 writeFieldsInDescendingOrder(message, writer); 2582 } else { 2583 if (proto3) { 2584 writeFieldsInAscendingOrderProto3(message, writer); 2585 } else { 2586 writeFieldsInAscendingOrderProto2(message, writer); 2587 } 2588 } 2589 } 2590 2591 @SuppressWarnings("unchecked") writeFieldsInAscendingOrderProto2(T message, Writer writer)2592 private void writeFieldsInAscendingOrderProto2(T message, Writer writer) throws IOException { 2593 Iterator<? extends Map.Entry<?, ?>> extensionIterator = null; 2594 Map.Entry nextExtension = null; 2595 if (hasExtensions) { 2596 FieldSet<?> extensions = extensionSchema.getExtensions(message); 2597 if (!extensions.isEmpty()) { 2598 extensionIterator = extensions.iterator(); 2599 nextExtension = extensionIterator.next(); 2600 } 2601 } 2602 int currentPresenceFieldOffset = NO_PRESENCE_SENTINEL; 2603 int currentPresenceField = 0; 2604 final int bufferLength = buffer.length; 2605 final sun.misc.Unsafe unsafe = UNSAFE; 2606 for (int pos = 0; pos < bufferLength; pos += INTS_PER_FIELD) { 2607 final int typeAndOffset = typeAndOffsetAt(pos); 2608 final int number = numberAt(pos); 2609 final int fieldType = type(typeAndOffset); 2610 2611 int presenceMaskAndOffset = 0; 2612 int presenceMask = 0; 2613 if (fieldType <= 17) { 2614 presenceMaskAndOffset = buffer[pos + 2]; 2615 final int presenceFieldOffset = presenceMaskAndOffset & OFFSET_MASK; 2616 if (presenceFieldOffset != currentPresenceFieldOffset) { 2617 currentPresenceFieldOffset = presenceFieldOffset; 2618 currentPresenceField = unsafe.getInt(message, (long) presenceFieldOffset); 2619 } 2620 presenceMask = 1 << (presenceMaskAndOffset >>> OFFSET_BITS); 2621 } 2622 2623 // Write any extensions that need to be written before the current field. 2624 while (nextExtension != null && extensionSchema.extensionNumber(nextExtension) <= number) { 2625 extensionSchema.serializeExtension(writer, nextExtension); 2626 nextExtension = extensionIterator.hasNext() ? extensionIterator.next() : null; 2627 } 2628 final long offset = offset(typeAndOffset); 2629 2630 switch (fieldType) { 2631 case 0: // DOUBLE: 2632 if ((currentPresenceField & presenceMask) != 0) { 2633 writer.writeDouble(number, doubleAt(message, offset)); 2634 } 2635 break; 2636 case 1: // FLOAT: 2637 if ((currentPresenceField & presenceMask) != 0) { 2638 writer.writeFloat(number, floatAt(message, offset)); 2639 } 2640 break; 2641 case 2: // INT64: 2642 if ((currentPresenceField & presenceMask) != 0) { 2643 writer.writeInt64(number, unsafe.getLong(message, offset)); 2644 } 2645 break; 2646 case 3: // UINT64: 2647 if ((currentPresenceField & presenceMask) != 0) { 2648 writer.writeUInt64(number, unsafe.getLong(message, offset)); 2649 } 2650 break; 2651 case 4: // INT32: 2652 if ((currentPresenceField & presenceMask) != 0) { 2653 writer.writeInt32(number, unsafe.getInt(message, offset)); 2654 } 2655 break; 2656 case 5: // FIXED64: 2657 if ((currentPresenceField & presenceMask) != 0) { 2658 writer.writeFixed64(number, unsafe.getLong(message, offset)); 2659 } 2660 break; 2661 case 6: // FIXED32: 2662 if ((currentPresenceField & presenceMask) != 0) { 2663 writer.writeFixed32(number, unsafe.getInt(message, offset)); 2664 } 2665 break; 2666 case 7: // BOOL: 2667 if ((currentPresenceField & presenceMask) != 0) { 2668 writer.writeBool(number, booleanAt(message, offset)); 2669 } 2670 break; 2671 case 8: // STRING: 2672 if ((currentPresenceField & presenceMask) != 0) { 2673 writeString(number, unsafe.getObject(message, offset), writer); 2674 } 2675 break; 2676 case 9: // MESSAGE: 2677 if ((currentPresenceField & presenceMask) != 0) { 2678 Object value = unsafe.getObject(message, offset); 2679 writer.writeMessage(number, value, getMessageFieldSchema(pos)); 2680 } 2681 break; 2682 case 10: // BYTES: 2683 if ((currentPresenceField & presenceMask) != 0) { 2684 writer.writeBytes(number, (ByteString) unsafe.getObject(message, offset)); 2685 } 2686 break; 2687 case 11: // UINT32: 2688 if ((currentPresenceField & presenceMask) != 0) { 2689 writer.writeUInt32(number, unsafe.getInt(message, offset)); 2690 } 2691 break; 2692 case 12: // ENUM: 2693 if ((currentPresenceField & presenceMask) != 0) { 2694 writer.writeEnum(number, unsafe.getInt(message, offset)); 2695 } 2696 break; 2697 case 13: // SFIXED32: 2698 if ((currentPresenceField & presenceMask) != 0) { 2699 writer.writeSFixed32(number, unsafe.getInt(message, offset)); 2700 } 2701 break; 2702 case 14: // SFIXED64: 2703 if ((currentPresenceField & presenceMask) != 0) { 2704 writer.writeSFixed64(number, unsafe.getLong(message, offset)); 2705 } 2706 break; 2707 case 15: // SINT32: 2708 if ((currentPresenceField & presenceMask) != 0) { 2709 writer.writeSInt32(number, unsafe.getInt(message, offset)); 2710 } 2711 break; 2712 case 16: // SINT64: 2713 if ((currentPresenceField & presenceMask) != 0) { 2714 writer.writeSInt64(number, unsafe.getLong(message, offset)); 2715 } 2716 break; 2717 case 17: // GROUP: 2718 if ((currentPresenceField & presenceMask) != 0) { 2719 writer.writeGroup( 2720 number, unsafe.getObject(message, offset), getMessageFieldSchema(pos)); 2721 } 2722 break; 2723 case 18: // DOUBLE_LIST: 2724 SchemaUtil.writeDoubleList( 2725 numberAt(pos), (List<Double>) unsafe.getObject(message, offset), writer, false); 2726 break; 2727 case 19: // FLOAT_LIST: 2728 SchemaUtil.writeFloatList( 2729 numberAt(pos), (List<Float>) unsafe.getObject(message, offset), writer, false); 2730 break; 2731 case 20: // INT64_LIST: 2732 SchemaUtil.writeInt64List( 2733 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, false); 2734 break; 2735 case 21: // UINT64_LIST: 2736 SchemaUtil.writeUInt64List( 2737 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, false); 2738 break; 2739 case 22: // INT32_LIST: 2740 SchemaUtil.writeInt32List( 2741 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, false); 2742 break; 2743 case 23: // FIXED64_LIST: 2744 SchemaUtil.writeFixed64List( 2745 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, false); 2746 break; 2747 case 24: // FIXED32_LIST: 2748 SchemaUtil.writeFixed32List( 2749 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, false); 2750 break; 2751 case 25: // BOOL_LIST: 2752 SchemaUtil.writeBoolList( 2753 numberAt(pos), (List<Boolean>) unsafe.getObject(message, offset), writer, false); 2754 break; 2755 case 26: // STRING_LIST: 2756 SchemaUtil.writeStringList( 2757 numberAt(pos), (List<String>) unsafe.getObject(message, offset), writer); 2758 break; 2759 case 27: // MESSAGE_LIST: 2760 SchemaUtil.writeMessageList( 2761 numberAt(pos), 2762 (List<?>) unsafe.getObject(message, offset), 2763 writer, 2764 getMessageFieldSchema(pos)); 2765 break; 2766 case 28: // BYTES_LIST: 2767 SchemaUtil.writeBytesList( 2768 numberAt(pos), (List<ByteString>) unsafe.getObject(message, offset), writer); 2769 break; 2770 case 29: // UINT32_LIST: 2771 SchemaUtil.writeUInt32List( 2772 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, false); 2773 break; 2774 case 30: // ENUM_LIST: 2775 SchemaUtil.writeEnumList( 2776 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, false); 2777 break; 2778 case 31: // SFIXED32_LIST: 2779 SchemaUtil.writeSFixed32List( 2780 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, false); 2781 break; 2782 case 32: // SFIXED64_LIST: 2783 SchemaUtil.writeSFixed64List( 2784 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, false); 2785 break; 2786 case 33: // SINT32_LIST: 2787 SchemaUtil.writeSInt32List( 2788 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, false); 2789 break; 2790 case 34: // SINT64_LIST: 2791 SchemaUtil.writeSInt64List( 2792 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, false); 2793 break; 2794 case 35: // DOUBLE_LIST_PACKED: 2795 // TODO(xiaofeng): Make use of cached field size to speed up serialization. 2796 SchemaUtil.writeDoubleList( 2797 numberAt(pos), (List<Double>) unsafe.getObject(message, offset), writer, true); 2798 break; 2799 case 36: // FLOAT_LIST_PACKED: 2800 SchemaUtil.writeFloatList( 2801 numberAt(pos), (List<Float>) unsafe.getObject(message, offset), writer, true); 2802 break; 2803 case 37: // INT64_LIST_PACKED: 2804 SchemaUtil.writeInt64List( 2805 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, true); 2806 break; 2807 case 38: // UINT64_LIST_PACKED: 2808 SchemaUtil.writeUInt64List( 2809 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, true); 2810 break; 2811 case 39: // INT32_LIST_PACKED: 2812 SchemaUtil.writeInt32List( 2813 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, true); 2814 break; 2815 case 40: // FIXED64_LIST_PACKED: 2816 SchemaUtil.writeFixed64List( 2817 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, true); 2818 break; 2819 case 41: // FIXED32_LIST_PACKED: 2820 SchemaUtil.writeFixed32List( 2821 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, true); 2822 2823 break; 2824 case 42: // BOOL_LIST_PACKED: 2825 SchemaUtil.writeBoolList( 2826 numberAt(pos), (List<Boolean>) unsafe.getObject(message, offset), writer, true); 2827 break; 2828 case 43: // UINT32_LIST_PACKED: 2829 SchemaUtil.writeUInt32List( 2830 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, true); 2831 break; 2832 case 44: // ENUM_LIST_PACKED: 2833 SchemaUtil.writeEnumList( 2834 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, true); 2835 break; 2836 case 45: // SFIXED32_LIST_PACKED: 2837 SchemaUtil.writeSFixed32List( 2838 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, true); 2839 break; 2840 case 46: // SFIXED64_LIST_PACKED: 2841 SchemaUtil.writeSFixed64List( 2842 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, true); 2843 break; 2844 case 47: // SINT32_LIST_PACKED: 2845 SchemaUtil.writeSInt32List( 2846 numberAt(pos), (List<Integer>) unsafe.getObject(message, offset), writer, true); 2847 break; 2848 case 48: // SINT64_LIST_PACKED: 2849 SchemaUtil.writeSInt64List( 2850 numberAt(pos), (List<Long>) unsafe.getObject(message, offset), writer, true); 2851 break; 2852 case 49: // GROUP_LIST: 2853 SchemaUtil.writeGroupList( 2854 numberAt(pos), 2855 (List<?>) unsafe.getObject(message, offset), 2856 writer, 2857 getMessageFieldSchema(pos)); 2858 break; 2859 case 50: // MAP: 2860 // TODO(dweis): Use schema cache. 2861 writeMapHelper(writer, number, unsafe.getObject(message, offset), pos); 2862 break; 2863 case 51: // ONEOF_DOUBLE: 2864 if (isOneofPresent(message, number, pos)) { 2865 writer.writeDouble(number, oneofDoubleAt(message, offset)); 2866 } 2867 break; 2868 case 52: // ONEOF_FLOAT: 2869 if (isOneofPresent(message, number, pos)) { 2870 writer.writeFloat(number, oneofFloatAt(message, offset)); 2871 } 2872 break; 2873 case 53: // ONEOF_INT64: 2874 if (isOneofPresent(message, number, pos)) { 2875 writer.writeInt64(number, oneofLongAt(message, offset)); 2876 } 2877 break; 2878 case 54: // ONEOF_UINT64: 2879 if (isOneofPresent(message, number, pos)) { 2880 writer.writeUInt64(number, oneofLongAt(message, offset)); 2881 } 2882 break; 2883 case 55: // ONEOF_INT32: 2884 if (isOneofPresent(message, number, pos)) { 2885 writer.writeInt32(number, oneofIntAt(message, offset)); 2886 } 2887 break; 2888 case 56: // ONEOF_FIXED64: 2889 if (isOneofPresent(message, number, pos)) { 2890 writer.writeFixed64(number, oneofLongAt(message, offset)); 2891 } 2892 break; 2893 case 57: // ONEOF_FIXED32: 2894 if (isOneofPresent(message, number, pos)) { 2895 writer.writeFixed32(number, oneofIntAt(message, offset)); 2896 } 2897 break; 2898 case 58: // ONEOF_BOOL: 2899 if (isOneofPresent(message, number, pos)) { 2900 writer.writeBool(number, oneofBooleanAt(message, offset)); 2901 } 2902 break; 2903 case 59: // ONEOF_STRING: 2904 if (isOneofPresent(message, number, pos)) { 2905 writeString(number, unsafe.getObject(message, offset), writer); 2906 } 2907 break; 2908 case 60: // ONEOF_MESSAGE: 2909 if (isOneofPresent(message, number, pos)) { 2910 Object value = unsafe.getObject(message, offset); 2911 writer.writeMessage(number, value, getMessageFieldSchema(pos)); 2912 } 2913 break; 2914 case 61: // ONEOF_BYTES: 2915 if (isOneofPresent(message, number, pos)) { 2916 writer.writeBytes(number, (ByteString) unsafe.getObject(message, offset)); 2917 } 2918 break; 2919 case 62: // ONEOF_UINT32: 2920 if (isOneofPresent(message, number, pos)) { 2921 writer.writeUInt32(number, oneofIntAt(message, offset)); 2922 } 2923 break; 2924 case 63: // ONEOF_ENUM: 2925 if (isOneofPresent(message, number, pos)) { 2926 writer.writeEnum(number, oneofIntAt(message, offset)); 2927 } 2928 break; 2929 case 64: // ONEOF_SFIXED32: 2930 if (isOneofPresent(message, number, pos)) { 2931 writer.writeSFixed32(number, oneofIntAt(message, offset)); 2932 } 2933 break; 2934 case 65: // ONEOF_SFIXED64: 2935 if (isOneofPresent(message, number, pos)) { 2936 writer.writeSFixed64(number, oneofLongAt(message, offset)); 2937 } 2938 break; 2939 case 66: // ONEOF_SINT32: 2940 if (isOneofPresent(message, number, pos)) { 2941 writer.writeSInt32(number, oneofIntAt(message, offset)); 2942 } 2943 break; 2944 case 67: // ONEOF_SINT64: 2945 if (isOneofPresent(message, number, pos)) { 2946 writer.writeSInt64(number, oneofLongAt(message, offset)); 2947 } 2948 break; 2949 case 68: // ONEOF_GROUP: 2950 if (isOneofPresent(message, number, pos)) { 2951 writer.writeGroup( 2952 number, unsafe.getObject(message, offset), getMessageFieldSchema(pos)); 2953 } 2954 break; 2955 default: 2956 // Assume it's an empty entry - just go to the next entry. 2957 break; 2958 } 2959 } 2960 while (nextExtension != null) { 2961 extensionSchema.serializeExtension(writer, nextExtension); 2962 nextExtension = extensionIterator.hasNext() ? extensionIterator.next() : null; 2963 } 2964 writeUnknownInMessageTo(unknownFieldSchema, message, writer); 2965 } 2966 2967 @SuppressWarnings("unchecked") writeFieldsInAscendingOrderProto3(T message, Writer writer)2968 private void writeFieldsInAscendingOrderProto3(T message, Writer writer) throws IOException { 2969 Iterator<? extends Map.Entry<?, ?>> extensionIterator = null; 2970 Map.Entry nextExtension = null; 2971 if (hasExtensions) { 2972 FieldSet<?> extensions = extensionSchema.getExtensions(message); 2973 if (!extensions.isEmpty()) { 2974 extensionIterator = extensions.iterator(); 2975 nextExtension = extensionIterator.next(); 2976 } 2977 } 2978 final int bufferLength = buffer.length; 2979 for (int pos = 0; pos < bufferLength; pos += INTS_PER_FIELD) { 2980 final int typeAndOffset = typeAndOffsetAt(pos); 2981 final int number = numberAt(pos); 2982 2983 // Write any extensions that need to be written before the current field. 2984 while (nextExtension != null && extensionSchema.extensionNumber(nextExtension) <= number) { 2985 extensionSchema.serializeExtension(writer, nextExtension); 2986 nextExtension = extensionIterator.hasNext() ? extensionIterator.next() : null; 2987 } 2988 2989 switch (type(typeAndOffset)) { 2990 case 0: // DOUBLE: 2991 if (isFieldPresent(message, pos)) { 2992 writer.writeDouble(number, doubleAt(message, offset(typeAndOffset))); 2993 } 2994 break; 2995 case 1: // FLOAT: 2996 if (isFieldPresent(message, pos)) { 2997 writer.writeFloat(number, floatAt(message, offset(typeAndOffset))); 2998 } 2999 break; 3000 case 2: // INT64: 3001 if (isFieldPresent(message, pos)) { 3002 writer.writeInt64(number, longAt(message, offset(typeAndOffset))); 3003 } 3004 break; 3005 case 3: // UINT64: 3006 if (isFieldPresent(message, pos)) { 3007 writer.writeUInt64(number, longAt(message, offset(typeAndOffset))); 3008 } 3009 break; 3010 case 4: // INT32: 3011 if (isFieldPresent(message, pos)) { 3012 writer.writeInt32(number, intAt(message, offset(typeAndOffset))); 3013 } 3014 break; 3015 case 5: // FIXED64: 3016 if (isFieldPresent(message, pos)) { 3017 writer.writeFixed64(number, longAt(message, offset(typeAndOffset))); 3018 } 3019 break; 3020 case 6: // FIXED32: 3021 if (isFieldPresent(message, pos)) { 3022 writer.writeFixed32(number, intAt(message, offset(typeAndOffset))); 3023 } 3024 break; 3025 case 7: // BOOL: 3026 if (isFieldPresent(message, pos)) { 3027 writer.writeBool(number, booleanAt(message, offset(typeAndOffset))); 3028 } 3029 break; 3030 case 8: // STRING: 3031 if (isFieldPresent(message, pos)) { 3032 writeString(number, UnsafeUtil.getObject(message, offset(typeAndOffset)), writer); 3033 } 3034 break; 3035 case 9: // MESSAGE: 3036 if (isFieldPresent(message, pos)) { 3037 Object value = UnsafeUtil.getObject(message, offset(typeAndOffset)); 3038 writer.writeMessage(number, value, getMessageFieldSchema(pos)); 3039 } 3040 break; 3041 case 10: // BYTES: 3042 if (isFieldPresent(message, pos)) { 3043 writer.writeBytes( 3044 number, (ByteString) UnsafeUtil.getObject(message, offset(typeAndOffset))); 3045 } 3046 break; 3047 case 11: // UINT32: 3048 if (isFieldPresent(message, pos)) { 3049 writer.writeUInt32(number, intAt(message, offset(typeAndOffset))); 3050 } 3051 break; 3052 case 12: // ENUM: 3053 if (isFieldPresent(message, pos)) { 3054 writer.writeEnum(number, intAt(message, offset(typeAndOffset))); 3055 } 3056 break; 3057 case 13: // SFIXED32: 3058 if (isFieldPresent(message, pos)) { 3059 writer.writeSFixed32(number, intAt(message, offset(typeAndOffset))); 3060 } 3061 break; 3062 case 14: // SFIXED64: 3063 if (isFieldPresent(message, pos)) { 3064 writer.writeSFixed64(number, longAt(message, offset(typeAndOffset))); 3065 } 3066 break; 3067 case 15: // SINT32: 3068 if (isFieldPresent(message, pos)) { 3069 writer.writeSInt32(number, intAt(message, offset(typeAndOffset))); 3070 } 3071 break; 3072 case 16: // SINT64: 3073 if (isFieldPresent(message, pos)) { 3074 writer.writeSInt64(number, longAt(message, offset(typeAndOffset))); 3075 } 3076 break; 3077 case 17: // GROUP: 3078 if (isFieldPresent(message, pos)) { 3079 writer.writeGroup( 3080 number, 3081 UnsafeUtil.getObject(message, offset(typeAndOffset)), 3082 getMessageFieldSchema(pos)); 3083 } 3084 break; 3085 case 18: // DOUBLE_LIST: 3086 SchemaUtil.writeDoubleList( 3087 numberAt(pos), 3088 (List<Double>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3089 writer, 3090 false); 3091 break; 3092 case 19: // FLOAT_LIST: 3093 SchemaUtil.writeFloatList( 3094 numberAt(pos), 3095 (List<Float>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3096 writer, 3097 false); 3098 break; 3099 case 20: // INT64_LIST: 3100 SchemaUtil.writeInt64List( 3101 numberAt(pos), 3102 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3103 writer, 3104 false); 3105 break; 3106 case 21: // UINT64_LIST: 3107 SchemaUtil.writeUInt64List( 3108 numberAt(pos), 3109 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3110 writer, 3111 false); 3112 break; 3113 case 22: // INT32_LIST: 3114 SchemaUtil.writeInt32List( 3115 numberAt(pos), 3116 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3117 writer, 3118 false); 3119 break; 3120 case 23: // FIXED64_LIST: 3121 SchemaUtil.writeFixed64List( 3122 numberAt(pos), 3123 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3124 writer, 3125 false); 3126 break; 3127 case 24: // FIXED32_LIST: 3128 SchemaUtil.writeFixed32List( 3129 numberAt(pos), 3130 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3131 writer, 3132 false); 3133 break; 3134 case 25: // BOOL_LIST: 3135 SchemaUtil.writeBoolList( 3136 numberAt(pos), 3137 (List<Boolean>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3138 writer, 3139 false); 3140 break; 3141 case 26: // STRING_LIST: 3142 SchemaUtil.writeStringList( 3143 numberAt(pos), 3144 (List<String>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3145 writer); 3146 break; 3147 case 27: // MESSAGE_LIST: 3148 SchemaUtil.writeMessageList( 3149 numberAt(pos), 3150 (List<?>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3151 writer, 3152 getMessageFieldSchema(pos)); 3153 break; 3154 case 28: // BYTES_LIST: 3155 SchemaUtil.writeBytesList( 3156 numberAt(pos), 3157 (List<ByteString>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3158 writer); 3159 break; 3160 case 29: // UINT32_LIST: 3161 SchemaUtil.writeUInt32List( 3162 numberAt(pos), 3163 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3164 writer, 3165 false); 3166 break; 3167 case 30: // ENUM_LIST: 3168 SchemaUtil.writeEnumList( 3169 numberAt(pos), 3170 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3171 writer, 3172 false); 3173 break; 3174 case 31: // SFIXED32_LIST: 3175 SchemaUtil.writeSFixed32List( 3176 numberAt(pos), 3177 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3178 writer, 3179 false); 3180 break; 3181 case 32: // SFIXED64_LIST: 3182 SchemaUtil.writeSFixed64List( 3183 numberAt(pos), 3184 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3185 writer, 3186 false); 3187 break; 3188 case 33: // SINT32_LIST: 3189 SchemaUtil.writeSInt32List( 3190 numberAt(pos), 3191 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3192 writer, 3193 false); 3194 break; 3195 case 34: // SINT64_LIST: 3196 SchemaUtil.writeSInt64List( 3197 numberAt(pos), 3198 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3199 writer, 3200 false); 3201 break; 3202 case 35: // DOUBLE_LIST_PACKED: 3203 // TODO(xiaofeng): Make use of cached field size to speed up serialization. 3204 SchemaUtil.writeDoubleList( 3205 numberAt(pos), 3206 (List<Double>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3207 writer, 3208 true); 3209 break; 3210 case 36: // FLOAT_LIST_PACKED: 3211 SchemaUtil.writeFloatList( 3212 numberAt(pos), 3213 (List<Float>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3214 writer, 3215 true); 3216 break; 3217 case 37: // INT64_LIST_PACKED: 3218 SchemaUtil.writeInt64List( 3219 numberAt(pos), 3220 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3221 writer, 3222 true); 3223 break; 3224 case 38: // UINT64_LIST_PACKED: 3225 SchemaUtil.writeUInt64List( 3226 numberAt(pos), 3227 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3228 writer, 3229 true); 3230 break; 3231 case 39: // INT32_LIST_PACKED: 3232 SchemaUtil.writeInt32List( 3233 numberAt(pos), 3234 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3235 writer, 3236 true); 3237 break; 3238 case 40: // FIXED64_LIST_PACKED: 3239 SchemaUtil.writeFixed64List( 3240 numberAt(pos), 3241 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3242 writer, 3243 true); 3244 break; 3245 case 41: // FIXED32_LIST_PACKED: 3246 SchemaUtil.writeFixed32List( 3247 numberAt(pos), 3248 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3249 writer, 3250 true); 3251 3252 break; 3253 case 42: // BOOL_LIST_PACKED: 3254 SchemaUtil.writeBoolList( 3255 numberAt(pos), 3256 (List<Boolean>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3257 writer, 3258 true); 3259 break; 3260 case 43: // UINT32_LIST_PACKED: 3261 SchemaUtil.writeUInt32List( 3262 numberAt(pos), 3263 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3264 writer, 3265 true); 3266 break; 3267 case 44: // ENUM_LIST_PACKED: 3268 SchemaUtil.writeEnumList( 3269 numberAt(pos), 3270 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3271 writer, 3272 true); 3273 break; 3274 case 45: // SFIXED32_LIST_PACKED: 3275 SchemaUtil.writeSFixed32List( 3276 numberAt(pos), 3277 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3278 writer, 3279 true); 3280 break; 3281 case 46: // SFIXED64_LIST_PACKED: 3282 SchemaUtil.writeSFixed64List( 3283 numberAt(pos), 3284 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3285 writer, 3286 true); 3287 break; 3288 case 47: // SINT32_LIST_PACKED: 3289 SchemaUtil.writeSInt32List( 3290 numberAt(pos), 3291 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3292 writer, 3293 true); 3294 break; 3295 case 48: // SINT64_LIST_PACKED: 3296 SchemaUtil.writeSInt64List( 3297 numberAt(pos), 3298 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3299 writer, 3300 true); 3301 break; 3302 case 49: // GROUP_LIST: 3303 SchemaUtil.writeGroupList( 3304 numberAt(pos), 3305 (List<?>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3306 writer, 3307 getMessageFieldSchema(pos)); 3308 break; 3309 case 50: // MAP: 3310 // TODO(dweis): Use schema cache. 3311 writeMapHelper(writer, number, UnsafeUtil.getObject(message, offset(typeAndOffset)), pos); 3312 break; 3313 case 51: // ONEOF_DOUBLE: 3314 if (isOneofPresent(message, number, pos)) { 3315 writer.writeDouble(number, oneofDoubleAt(message, offset(typeAndOffset))); 3316 } 3317 break; 3318 case 52: // ONEOF_FLOAT: 3319 if (isOneofPresent(message, number, pos)) { 3320 writer.writeFloat(number, oneofFloatAt(message, offset(typeAndOffset))); 3321 } 3322 break; 3323 case 53: // ONEOF_INT64: 3324 if (isOneofPresent(message, number, pos)) { 3325 writer.writeInt64(number, oneofLongAt(message, offset(typeAndOffset))); 3326 } 3327 break; 3328 case 54: // ONEOF_UINT64: 3329 if (isOneofPresent(message, number, pos)) { 3330 writer.writeUInt64(number, oneofLongAt(message, offset(typeAndOffset))); 3331 } 3332 break; 3333 case 55: // ONEOF_INT32: 3334 if (isOneofPresent(message, number, pos)) { 3335 writer.writeInt32(number, oneofIntAt(message, offset(typeAndOffset))); 3336 } 3337 break; 3338 case 56: // ONEOF_FIXED64: 3339 if (isOneofPresent(message, number, pos)) { 3340 writer.writeFixed64(number, oneofLongAt(message, offset(typeAndOffset))); 3341 } 3342 break; 3343 case 57: // ONEOF_FIXED32: 3344 if (isOneofPresent(message, number, pos)) { 3345 writer.writeFixed32(number, oneofIntAt(message, offset(typeAndOffset))); 3346 } 3347 break; 3348 case 58: // ONEOF_BOOL: 3349 if (isOneofPresent(message, number, pos)) { 3350 writer.writeBool(number, oneofBooleanAt(message, offset(typeAndOffset))); 3351 } 3352 break; 3353 case 59: // ONEOF_STRING: 3354 if (isOneofPresent(message, number, pos)) { 3355 writeString(number, UnsafeUtil.getObject(message, offset(typeAndOffset)), writer); 3356 } 3357 break; 3358 case 60: // ONEOF_MESSAGE: 3359 if (isOneofPresent(message, number, pos)) { 3360 Object value = UnsafeUtil.getObject(message, offset(typeAndOffset)); 3361 writer.writeMessage(number, value, getMessageFieldSchema(pos)); 3362 } 3363 break; 3364 case 61: // ONEOF_BYTES: 3365 if (isOneofPresent(message, number, pos)) { 3366 writer.writeBytes( 3367 number, (ByteString) UnsafeUtil.getObject(message, offset(typeAndOffset))); 3368 } 3369 break; 3370 case 62: // ONEOF_UINT32: 3371 if (isOneofPresent(message, number, pos)) { 3372 writer.writeUInt32(number, oneofIntAt(message, offset(typeAndOffset))); 3373 } 3374 break; 3375 case 63: // ONEOF_ENUM: 3376 if (isOneofPresent(message, number, pos)) { 3377 writer.writeEnum(number, oneofIntAt(message, offset(typeAndOffset))); 3378 } 3379 break; 3380 case 64: // ONEOF_SFIXED32: 3381 if (isOneofPresent(message, number, pos)) { 3382 writer.writeSFixed32(number, oneofIntAt(message, offset(typeAndOffset))); 3383 } 3384 break; 3385 case 65: // ONEOF_SFIXED64: 3386 if (isOneofPresent(message, number, pos)) { 3387 writer.writeSFixed64(number, oneofLongAt(message, offset(typeAndOffset))); 3388 } 3389 break; 3390 case 66: // ONEOF_SINT32: 3391 if (isOneofPresent(message, number, pos)) { 3392 writer.writeSInt32(number, oneofIntAt(message, offset(typeAndOffset))); 3393 } 3394 break; 3395 case 67: // ONEOF_SINT64: 3396 if (isOneofPresent(message, number, pos)) { 3397 writer.writeSInt64(number, oneofLongAt(message, offset(typeAndOffset))); 3398 } 3399 break; 3400 case 68: // ONEOF_GROUP: 3401 if (isOneofPresent(message, number, pos)) { 3402 writer.writeGroup( 3403 number, 3404 UnsafeUtil.getObject(message, offset(typeAndOffset)), 3405 getMessageFieldSchema(pos)); 3406 } 3407 break; 3408 default: 3409 // Assume it's an empty entry - just go to the next entry. 3410 break; 3411 } 3412 } 3413 while (nextExtension != null) { 3414 extensionSchema.serializeExtension(writer, nextExtension); 3415 nextExtension = extensionIterator.hasNext() ? extensionIterator.next() : null; 3416 } 3417 writeUnknownInMessageTo(unknownFieldSchema, message, writer); 3418 } 3419 3420 @SuppressWarnings("unchecked") writeFieldsInDescendingOrder(T message, Writer writer)3421 private void writeFieldsInDescendingOrder(T message, Writer writer) throws IOException { 3422 writeUnknownInMessageTo(unknownFieldSchema, message, writer); 3423 3424 Iterator<? extends Map.Entry<?, ?>> extensionIterator = null; 3425 Map.Entry nextExtension = null; 3426 if (hasExtensions) { 3427 FieldSet<?> extensions = extensionSchema.getExtensions(message); 3428 if (!extensions.isEmpty()) { 3429 extensionIterator = extensions.descendingIterator(); 3430 nextExtension = extensionIterator.next(); 3431 } 3432 } 3433 3434 for (int pos = buffer.length - INTS_PER_FIELD; pos >= 0; pos -= INTS_PER_FIELD) { 3435 final int typeAndOffset = typeAndOffsetAt(pos); 3436 final int number = numberAt(pos); 3437 3438 // Write any extensions that need to be written before the current field. 3439 while (nextExtension != null && extensionSchema.extensionNumber(nextExtension) > number) { 3440 extensionSchema.serializeExtension(writer, nextExtension); 3441 nextExtension = extensionIterator.hasNext() ? extensionIterator.next() : null; 3442 } 3443 3444 switch (type(typeAndOffset)) { 3445 case 0: // DOUBLE: 3446 if (isFieldPresent(message, pos)) { 3447 writer.writeDouble(number, doubleAt(message, offset(typeAndOffset))); 3448 } 3449 break; 3450 case 1: // FLOAT: 3451 if (isFieldPresent(message, pos)) { 3452 writer.writeFloat(number, floatAt(message, offset(typeAndOffset))); 3453 } 3454 break; 3455 case 2: // INT64: 3456 if (isFieldPresent(message, pos)) { 3457 writer.writeInt64(number, longAt(message, offset(typeAndOffset))); 3458 } 3459 break; 3460 case 3: // UINT64: 3461 if (isFieldPresent(message, pos)) { 3462 writer.writeUInt64(number, longAt(message, offset(typeAndOffset))); 3463 } 3464 break; 3465 case 4: // INT32: 3466 if (isFieldPresent(message, pos)) { 3467 writer.writeInt32(number, intAt(message, offset(typeAndOffset))); 3468 } 3469 break; 3470 case 5: // FIXED64: 3471 if (isFieldPresent(message, pos)) { 3472 writer.writeFixed64(number, longAt(message, offset(typeAndOffset))); 3473 } 3474 break; 3475 case 6: // FIXED32: 3476 if (isFieldPresent(message, pos)) { 3477 writer.writeFixed32(number, intAt(message, offset(typeAndOffset))); 3478 } 3479 break; 3480 case 7: // BOOL: 3481 if (isFieldPresent(message, pos)) { 3482 writer.writeBool(number, booleanAt(message, offset(typeAndOffset))); 3483 } 3484 break; 3485 case 8: // STRING: 3486 if (isFieldPresent(message, pos)) { 3487 writeString(number, UnsafeUtil.getObject(message, offset(typeAndOffset)), writer); 3488 } 3489 break; 3490 case 9: // MESSAGE: 3491 if (isFieldPresent(message, pos)) { 3492 Object value = UnsafeUtil.getObject(message, offset(typeAndOffset)); 3493 writer.writeMessage(number, value, getMessageFieldSchema(pos)); 3494 } 3495 break; 3496 case 10: // BYTES: 3497 if (isFieldPresent(message, pos)) { 3498 writer.writeBytes( 3499 number, (ByteString) UnsafeUtil.getObject(message, offset(typeAndOffset))); 3500 } 3501 break; 3502 case 11: // UINT32: 3503 if (isFieldPresent(message, pos)) { 3504 writer.writeUInt32(number, intAt(message, offset(typeAndOffset))); 3505 } 3506 break; 3507 case 12: // ENUM: 3508 if (isFieldPresent(message, pos)) { 3509 writer.writeEnum(number, intAt(message, offset(typeAndOffset))); 3510 } 3511 break; 3512 case 13: // SFIXED32: 3513 if (isFieldPresent(message, pos)) { 3514 writer.writeSFixed32(number, intAt(message, offset(typeAndOffset))); 3515 } 3516 break; 3517 case 14: // SFIXED64: 3518 if (isFieldPresent(message, pos)) { 3519 writer.writeSFixed64(number, longAt(message, offset(typeAndOffset))); 3520 } 3521 break; 3522 case 15: // SINT32: 3523 if (isFieldPresent(message, pos)) { 3524 writer.writeSInt32(number, intAt(message, offset(typeAndOffset))); 3525 } 3526 break; 3527 case 16: // SINT64: 3528 if (isFieldPresent(message, pos)) { 3529 writer.writeSInt64(number, longAt(message, offset(typeAndOffset))); 3530 } 3531 break; 3532 case 17: // GROUP: 3533 if (isFieldPresent(message, pos)) { 3534 writer.writeGroup( 3535 number, 3536 UnsafeUtil.getObject(message, offset(typeAndOffset)), 3537 getMessageFieldSchema(pos)); 3538 } 3539 break; 3540 case 18: // DOUBLE_LIST: 3541 SchemaUtil.writeDoubleList( 3542 numberAt(pos), 3543 (List<Double>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3544 writer, 3545 false); 3546 break; 3547 case 19: // FLOAT_LIST: 3548 SchemaUtil.writeFloatList( 3549 numberAt(pos), 3550 (List<Float>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3551 writer, 3552 false); 3553 break; 3554 case 20: // INT64_LIST: 3555 SchemaUtil.writeInt64List( 3556 numberAt(pos), 3557 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3558 writer, 3559 false); 3560 break; 3561 case 21: // UINT64_LIST: 3562 SchemaUtil.writeUInt64List( 3563 numberAt(pos), 3564 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3565 writer, 3566 false); 3567 break; 3568 case 22: // INT32_LIST: 3569 SchemaUtil.writeInt32List( 3570 numberAt(pos), 3571 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3572 writer, 3573 false); 3574 break; 3575 case 23: // FIXED64_LIST: 3576 SchemaUtil.writeFixed64List( 3577 numberAt(pos), 3578 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3579 writer, 3580 false); 3581 break; 3582 case 24: // FIXED32_LIST: 3583 SchemaUtil.writeFixed32List( 3584 numberAt(pos), 3585 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3586 writer, 3587 false); 3588 break; 3589 case 25: // BOOL_LIST: 3590 SchemaUtil.writeBoolList( 3591 numberAt(pos), 3592 (List<Boolean>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3593 writer, 3594 false); 3595 break; 3596 case 26: // STRING_LIST: 3597 SchemaUtil.writeStringList( 3598 numberAt(pos), 3599 (List<String>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3600 writer); 3601 break; 3602 case 27: // MESSAGE_LIST: 3603 SchemaUtil.writeMessageList( 3604 numberAt(pos), 3605 (List<?>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3606 writer, 3607 getMessageFieldSchema(pos)); 3608 break; 3609 case 28: // BYTES_LIST: 3610 SchemaUtil.writeBytesList( 3611 numberAt(pos), 3612 (List<ByteString>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3613 writer); 3614 break; 3615 case 29: // UINT32_LIST: 3616 SchemaUtil.writeUInt32List( 3617 numberAt(pos), 3618 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3619 writer, 3620 false); 3621 break; 3622 case 30: // ENUM_LIST: 3623 SchemaUtil.writeEnumList( 3624 numberAt(pos), 3625 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3626 writer, 3627 false); 3628 break; 3629 case 31: // SFIXED32_LIST: 3630 SchemaUtil.writeSFixed32List( 3631 numberAt(pos), 3632 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3633 writer, 3634 false); 3635 break; 3636 case 32: // SFIXED64_LIST: 3637 SchemaUtil.writeSFixed64List( 3638 numberAt(pos), 3639 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3640 writer, 3641 false); 3642 break; 3643 case 33: // SINT32_LIST: 3644 SchemaUtil.writeSInt32List( 3645 numberAt(pos), 3646 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3647 writer, 3648 false); 3649 break; 3650 case 34: // SINT64_LIST: 3651 SchemaUtil.writeSInt64List( 3652 numberAt(pos), 3653 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3654 writer, 3655 false); 3656 break; 3657 case 35: // DOUBLE_LIST_PACKED: 3658 SchemaUtil.writeDoubleList( 3659 numberAt(pos), 3660 (List<Double>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3661 writer, 3662 true); 3663 break; 3664 case 36: // FLOAT_LIST_PACKED: 3665 SchemaUtil.writeFloatList( 3666 numberAt(pos), 3667 (List<Float>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3668 writer, 3669 true); 3670 break; 3671 case 37: // INT64_LIST_PACKED: 3672 SchemaUtil.writeInt64List( 3673 numberAt(pos), 3674 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3675 writer, 3676 true); 3677 break; 3678 case 38: // UINT64_LIST_PACKED: 3679 SchemaUtil.writeUInt64List( 3680 numberAt(pos), 3681 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3682 writer, 3683 true); 3684 break; 3685 case 39: // INT32_LIST_PACKED: 3686 SchemaUtil.writeInt32List( 3687 numberAt(pos), 3688 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3689 writer, 3690 true); 3691 break; 3692 case 40: // FIXED64_LIST_PACKED: 3693 SchemaUtil.writeFixed64List( 3694 numberAt(pos), 3695 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3696 writer, 3697 true); 3698 break; 3699 case 41: // FIXED32_LIST_PACKED: 3700 SchemaUtil.writeFixed32List( 3701 numberAt(pos), 3702 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3703 writer, 3704 true); 3705 3706 break; 3707 case 42: // BOOL_LIST_PACKED: 3708 SchemaUtil.writeBoolList( 3709 numberAt(pos), 3710 (List<Boolean>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3711 writer, 3712 true); 3713 break; 3714 case 43: // UINT32_LIST_PACKED: 3715 SchemaUtil.writeUInt32List( 3716 numberAt(pos), 3717 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3718 writer, 3719 true); 3720 break; 3721 case 44: // ENUM_LIST_PACKED: 3722 SchemaUtil.writeEnumList( 3723 numberAt(pos), 3724 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3725 writer, 3726 true); 3727 break; 3728 case 45: // SFIXED32_LIST_PACKED: 3729 SchemaUtil.writeSFixed32List( 3730 numberAt(pos), 3731 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3732 writer, 3733 true); 3734 break; 3735 case 46: // SFIXED64_LIST_PACKED: 3736 SchemaUtil.writeSFixed64List( 3737 numberAt(pos), 3738 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3739 writer, 3740 true); 3741 break; 3742 case 47: // SINT32_LIST_PACKED: 3743 SchemaUtil.writeSInt32List( 3744 numberAt(pos), 3745 (List<Integer>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3746 writer, 3747 true); 3748 break; 3749 case 48: // SINT64_LIST_PACKED: 3750 SchemaUtil.writeSInt64List( 3751 numberAt(pos), 3752 (List<Long>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3753 writer, 3754 true); 3755 break; 3756 case 49: // GROUP_LIST: 3757 SchemaUtil.writeGroupList( 3758 numberAt(pos), 3759 (List<?>) UnsafeUtil.getObject(message, offset(typeAndOffset)), 3760 writer, 3761 getMessageFieldSchema(pos)); 3762 break; 3763 case 50: // MAP: 3764 // TODO(dweis): Use schema cache. 3765 writeMapHelper(writer, number, UnsafeUtil.getObject(message, offset(typeAndOffset)), pos); 3766 break; 3767 case 51: // ONEOF_DOUBLE: 3768 if (isOneofPresent(message, number, pos)) { 3769 writer.writeDouble(number, oneofDoubleAt(message, offset(typeAndOffset))); 3770 } 3771 break; 3772 case 52: // ONEOF_FLOAT: 3773 if (isOneofPresent(message, number, pos)) { 3774 writer.writeFloat(number, oneofFloatAt(message, offset(typeAndOffset))); 3775 } 3776 break; 3777 case 53: // ONEOF_INT64: 3778 if (isOneofPresent(message, number, pos)) { 3779 writer.writeInt64(number, oneofLongAt(message, offset(typeAndOffset))); 3780 } 3781 break; 3782 case 54: // ONEOF_UINT64: 3783 if (isOneofPresent(message, number, pos)) { 3784 writer.writeUInt64(number, oneofLongAt(message, offset(typeAndOffset))); 3785 } 3786 break; 3787 case 55: // ONEOF_INT32: 3788 if (isOneofPresent(message, number, pos)) { 3789 writer.writeInt32(number, oneofIntAt(message, offset(typeAndOffset))); 3790 } 3791 break; 3792 case 56: // ONEOF_FIXED64: 3793 if (isOneofPresent(message, number, pos)) { 3794 writer.writeFixed64(number, oneofLongAt(message, offset(typeAndOffset))); 3795 } 3796 break; 3797 case 57: // ONEOF_FIXED32: 3798 if (isOneofPresent(message, number, pos)) { 3799 writer.writeFixed32(number, oneofIntAt(message, offset(typeAndOffset))); 3800 } 3801 break; 3802 case 58: // ONEOF_BOOL: 3803 if (isOneofPresent(message, number, pos)) { 3804 writer.writeBool(number, oneofBooleanAt(message, offset(typeAndOffset))); 3805 } 3806 break; 3807 case 59: // ONEOF_STRING: 3808 if (isOneofPresent(message, number, pos)) { 3809 writeString(number, UnsafeUtil.getObject(message, offset(typeAndOffset)), writer); 3810 } 3811 break; 3812 case 60: // ONEOF_MESSAGE: 3813 if (isOneofPresent(message, number, pos)) { 3814 Object value = UnsafeUtil.getObject(message, offset(typeAndOffset)); 3815 writer.writeMessage(number, value, getMessageFieldSchema(pos)); 3816 } 3817 break; 3818 case 61: // ONEOF_BYTES: 3819 if (isOneofPresent(message, number, pos)) { 3820 writer.writeBytes( 3821 number, (ByteString) UnsafeUtil.getObject(message, offset(typeAndOffset))); 3822 } 3823 break; 3824 case 62: // ONEOF_UINT32: 3825 if (isOneofPresent(message, number, pos)) { 3826 writer.writeUInt32(number, oneofIntAt(message, offset(typeAndOffset))); 3827 } 3828 break; 3829 case 63: // ONEOF_ENUM: 3830 if (isOneofPresent(message, number, pos)) { 3831 writer.writeEnum(number, oneofIntAt(message, offset(typeAndOffset))); 3832 } 3833 break; 3834 case 64: // ONEOF_SFIXED32: 3835 if (isOneofPresent(message, number, pos)) { 3836 writer.writeSFixed32(number, oneofIntAt(message, offset(typeAndOffset))); 3837 } 3838 break; 3839 case 65: // ONEOF_SFIXED64: 3840 if (isOneofPresent(message, number, pos)) { 3841 writer.writeSFixed64(number, oneofLongAt(message, offset(typeAndOffset))); 3842 } 3843 break; 3844 case 66: // ONEOF_SINT32: 3845 if (isOneofPresent(message, number, pos)) { 3846 writer.writeSInt32(number, oneofIntAt(message, offset(typeAndOffset))); 3847 } 3848 break; 3849 case 67: // ONEOF_SINT64: 3850 if (isOneofPresent(message, number, pos)) { 3851 writer.writeSInt64(number, oneofLongAt(message, offset(typeAndOffset))); 3852 } 3853 break; 3854 case 68: // ONEOF_GROUP: 3855 if (isOneofPresent(message, number, pos)) { 3856 writer.writeGroup( 3857 number, 3858 UnsafeUtil.getObject(message, offset(typeAndOffset)), 3859 getMessageFieldSchema(pos)); 3860 } 3861 break; 3862 default: 3863 break; 3864 } 3865 } 3866 while (nextExtension != null) { 3867 extensionSchema.serializeExtension(writer, nextExtension); 3868 nextExtension = extensionIterator.hasNext() ? extensionIterator.next() : null; 3869 } 3870 } 3871 3872 @SuppressWarnings("unchecked") writeMapHelper(Writer writer, int number, Object mapField, int pos)3873 private <K, V> void writeMapHelper(Writer writer, int number, Object mapField, int pos) 3874 throws IOException { 3875 if (mapField != null) { 3876 writer.writeMap( 3877 number, 3878 (MapEntryLite.Metadata<K, V>) mapFieldSchema.forMapMetadata(getMapFieldDefaultEntry(pos)), 3879 (Map<K, V>) mapFieldSchema.forMapData(mapField)); 3880 } 3881 } 3882 writeUnknownInMessageTo( UnknownFieldSchema<UT, UB> schema, T message, Writer writer)3883 private <UT, UB> void writeUnknownInMessageTo( 3884 UnknownFieldSchema<UT, UB> schema, T message, Writer writer) throws IOException { 3885 schema.writeTo(schema.getFromMessage(message), writer); 3886 } 3887 3888 @Override mergeFrom(T message, Reader reader, ExtensionRegistryLite extensionRegistry)3889 public void mergeFrom(T message, Reader reader, ExtensionRegistryLite extensionRegistry) 3890 throws IOException { 3891 if (extensionRegistry == null) { 3892 throw new NullPointerException(); 3893 } 3894 checkMutable(message); 3895 mergeFromHelper(unknownFieldSchema, extensionSchema, message, reader, extensionRegistry); 3896 } 3897 3898 /** 3899 * A helper method for wildcard capture of {@code unknownFieldSchema}. See: 3900 * https://docs.oracle.com/javase/tutorial/java/generics/capture.html 3901 */ mergeFromHelper( UnknownFieldSchema<UT, UB> unknownFieldSchema, ExtensionSchema<ET> extensionSchema, T message, Reader reader, ExtensionRegistryLite extensionRegistry)3902 private <UT, UB, ET extends FieldDescriptorLite<ET>> void mergeFromHelper( 3903 UnknownFieldSchema<UT, UB> unknownFieldSchema, 3904 ExtensionSchema<ET> extensionSchema, 3905 T message, 3906 Reader reader, 3907 ExtensionRegistryLite extensionRegistry) 3908 throws IOException { 3909 UB unknownFields = null; 3910 FieldSet<ET> extensions = null; 3911 try { 3912 while (true) { 3913 final int number = reader.getFieldNumber(); 3914 final int pos = positionForFieldNumber(number); 3915 if (pos < 0) { 3916 if (number == Reader.READ_DONE) { 3917 return; 3918 } 3919 // Check if it's an extension. 3920 Object extension = 3921 !hasExtensions 3922 ? null 3923 : extensionSchema.findExtensionByNumber( 3924 extensionRegistry, defaultInstance, number); 3925 if (extension != null) { 3926 if (extensions == null) { 3927 extensions = extensionSchema.getMutableExtensions(message); 3928 } 3929 unknownFields = 3930 extensionSchema.parseExtension( 3931 message, 3932 reader, 3933 extension, 3934 extensionRegistry, 3935 extensions, 3936 unknownFields, 3937 unknownFieldSchema); 3938 continue; 3939 } 3940 if (unknownFieldSchema.shouldDiscardUnknownFields(reader)) { 3941 if (reader.skipField()) { 3942 continue; 3943 } 3944 } else { 3945 if (unknownFields == null) { 3946 unknownFields = unknownFieldSchema.getBuilderFromMessage(message); 3947 } 3948 // Unknown field. 3949 if (unknownFieldSchema.mergeOneFieldFrom(unknownFields, reader)) { 3950 continue; 3951 } 3952 } 3953 // Done reading. 3954 return; 3955 } 3956 final int typeAndOffset = typeAndOffsetAt(pos); 3957 3958 try { 3959 switch (type(typeAndOffset)) { 3960 case 0: // DOUBLE: 3961 UnsafeUtil.putDouble(message, offset(typeAndOffset), reader.readDouble()); 3962 setFieldPresent(message, pos); 3963 break; 3964 case 1: // FLOAT: 3965 UnsafeUtil.putFloat(message, offset(typeAndOffset), reader.readFloat()); 3966 setFieldPresent(message, pos); 3967 break; 3968 case 2: // INT64: 3969 UnsafeUtil.putLong(message, offset(typeAndOffset), reader.readInt64()); 3970 setFieldPresent(message, pos); 3971 break; 3972 case 3: // UINT64: 3973 UnsafeUtil.putLong(message, offset(typeAndOffset), reader.readUInt64()); 3974 setFieldPresent(message, pos); 3975 break; 3976 case 4: // INT32: 3977 UnsafeUtil.putInt(message, offset(typeAndOffset), reader.readInt32()); 3978 setFieldPresent(message, pos); 3979 break; 3980 case 5: // FIXED64: 3981 UnsafeUtil.putLong(message, offset(typeAndOffset), reader.readFixed64()); 3982 setFieldPresent(message, pos); 3983 break; 3984 case 6: // FIXED32: 3985 UnsafeUtil.putInt(message, offset(typeAndOffset), reader.readFixed32()); 3986 setFieldPresent(message, pos); 3987 break; 3988 case 7: // BOOL: 3989 UnsafeUtil.putBoolean(message, offset(typeAndOffset), reader.readBool()); 3990 setFieldPresent(message, pos); 3991 break; 3992 case 8: // STRING: 3993 readString(message, typeAndOffset, reader); 3994 setFieldPresent(message, pos); 3995 break; 3996 case 9: 3997 { // MESSAGE: 3998 final MessageLite current = (MessageLite) mutableMessageFieldForMerge(message, pos); 3999 reader.mergeMessageField( 4000 current, (Schema<MessageLite>) getMessageFieldSchema(pos), extensionRegistry); 4001 storeMessageField(message, pos, current); 4002 break; 4003 } 4004 case 10: // BYTES: 4005 UnsafeUtil.putObject(message, offset(typeAndOffset), reader.readBytes()); 4006 setFieldPresent(message, pos); 4007 break; 4008 case 11: // UINT32: 4009 UnsafeUtil.putInt(message, offset(typeAndOffset), reader.readUInt32()); 4010 setFieldPresent(message, pos); 4011 break; 4012 case 12: // ENUM: 4013 { 4014 int enumValue = reader.readEnum(); 4015 EnumVerifier enumVerifier = getEnumFieldVerifier(pos); 4016 if (enumVerifier == null || enumVerifier.isInRange(enumValue)) { 4017 UnsafeUtil.putInt(message, offset(typeAndOffset), enumValue); 4018 setFieldPresent(message, pos); 4019 } else { 4020 unknownFields = 4021 SchemaUtil.storeUnknownEnum( 4022 message, number, enumValue, unknownFields, unknownFieldSchema); 4023 } 4024 break; 4025 } 4026 case 13: // SFIXED32: 4027 UnsafeUtil.putInt(message, offset(typeAndOffset), reader.readSFixed32()); 4028 setFieldPresent(message, pos); 4029 break; 4030 case 14: // SFIXED64: 4031 UnsafeUtil.putLong(message, offset(typeAndOffset), reader.readSFixed64()); 4032 setFieldPresent(message, pos); 4033 break; 4034 case 15: // SINT32: 4035 UnsafeUtil.putInt(message, offset(typeAndOffset), reader.readSInt32()); 4036 setFieldPresent(message, pos); 4037 break; 4038 case 16: // SINT64: 4039 UnsafeUtil.putLong(message, offset(typeAndOffset), reader.readSInt64()); 4040 setFieldPresent(message, pos); 4041 break; 4042 case 17: 4043 { // GROUP: 4044 final MessageLite current = (MessageLite) mutableMessageFieldForMerge(message, pos); 4045 reader.mergeGroupField( 4046 current, (Schema<MessageLite>) getMessageFieldSchema(pos), extensionRegistry); 4047 storeMessageField(message, pos, current); 4048 break; 4049 } 4050 case 18: // DOUBLE_LIST: 4051 reader.readDoubleList( 4052 listFieldSchema.<Double>mutableListAt(message, offset(typeAndOffset))); 4053 break; 4054 case 19: // FLOAT_LIST: 4055 reader.readFloatList( 4056 listFieldSchema.<Float>mutableListAt(message, offset(typeAndOffset))); 4057 break; 4058 case 20: // INT64_LIST: 4059 reader.readInt64List( 4060 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4061 break; 4062 case 21: // UINT64_LIST: 4063 reader.readUInt64List( 4064 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4065 break; 4066 case 22: // INT32_LIST: 4067 reader.readInt32List( 4068 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4069 break; 4070 case 23: // FIXED64_LIST: 4071 reader.readFixed64List( 4072 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4073 break; 4074 case 24: // FIXED32_LIST: 4075 reader.readFixed32List( 4076 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4077 break; 4078 case 25: // BOOL_LIST: 4079 reader.readBoolList( 4080 listFieldSchema.<Boolean>mutableListAt(message, offset(typeAndOffset))); 4081 break; 4082 case 26: // STRING_LIST: 4083 readStringList(message, typeAndOffset, reader); 4084 break; 4085 case 27: 4086 { // MESSAGE_LIST: 4087 readMessageList( 4088 message, 4089 typeAndOffset, 4090 reader, 4091 (Schema<T>) getMessageFieldSchema(pos), 4092 extensionRegistry); 4093 break; 4094 } 4095 case 28: // BYTES_LIST: 4096 reader.readBytesList( 4097 listFieldSchema.<ByteString>mutableListAt(message, offset(typeAndOffset))); 4098 break; 4099 case 29: // UINT32_LIST: 4100 reader.readUInt32List( 4101 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4102 break; 4103 case 30: // ENUM_LIST: 4104 { 4105 List<Integer> enumList = 4106 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset)); 4107 reader.readEnumList(enumList); 4108 unknownFields = 4109 SchemaUtil.filterUnknownEnumList( 4110 message, 4111 number, 4112 enumList, 4113 getEnumFieldVerifier(pos), 4114 unknownFields, 4115 unknownFieldSchema); 4116 break; 4117 } 4118 case 31: // SFIXED32_LIST: 4119 reader.readSFixed32List( 4120 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4121 break; 4122 case 32: // SFIXED64_LIST: 4123 reader.readSFixed64List( 4124 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4125 break; 4126 case 33: // SINT32_LIST: 4127 reader.readSInt32List( 4128 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4129 break; 4130 case 34: // SINT64_LIST: 4131 reader.readSInt64List( 4132 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4133 break; 4134 case 35: // DOUBLE_LIST_PACKED: 4135 reader.readDoubleList( 4136 listFieldSchema.<Double>mutableListAt(message, offset(typeAndOffset))); 4137 break; 4138 case 36: // FLOAT_LIST_PACKED: 4139 reader.readFloatList( 4140 listFieldSchema.<Float>mutableListAt(message, offset(typeAndOffset))); 4141 break; 4142 case 37: // INT64_LIST_PACKED: 4143 reader.readInt64List( 4144 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4145 break; 4146 case 38: // UINT64_LIST_PACKED: 4147 reader.readUInt64List( 4148 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4149 break; 4150 case 39: // INT32_LIST_PACKED: 4151 reader.readInt32List( 4152 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4153 break; 4154 case 40: // FIXED64_LIST_PACKED: 4155 reader.readFixed64List( 4156 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4157 break; 4158 case 41: // FIXED32_LIST_PACKED: 4159 reader.readFixed32List( 4160 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4161 break; 4162 case 42: // BOOL_LIST_PACKED: 4163 reader.readBoolList( 4164 listFieldSchema.<Boolean>mutableListAt(message, offset(typeAndOffset))); 4165 break; 4166 case 43: // UINT32_LIST_PACKED: 4167 reader.readUInt32List( 4168 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4169 break; 4170 case 44: // ENUM_LIST_PACKED: 4171 { 4172 List<Integer> enumList = 4173 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset)); 4174 reader.readEnumList(enumList); 4175 unknownFields = 4176 SchemaUtil.filterUnknownEnumList( 4177 message, 4178 number, 4179 enumList, 4180 getEnumFieldVerifier(pos), 4181 unknownFields, 4182 unknownFieldSchema); 4183 break; 4184 } 4185 case 45: // SFIXED32_LIST_PACKED: 4186 reader.readSFixed32List( 4187 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4188 break; 4189 case 46: // SFIXED64_LIST_PACKED: 4190 reader.readSFixed64List( 4191 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4192 break; 4193 case 47: // SINT32_LIST_PACKED: 4194 reader.readSInt32List( 4195 listFieldSchema.<Integer>mutableListAt(message, offset(typeAndOffset))); 4196 break; 4197 case 48: // SINT64_LIST_PACKED: 4198 reader.readSInt64List( 4199 listFieldSchema.<Long>mutableListAt(message, offset(typeAndOffset))); 4200 break; 4201 case 49: 4202 { // GROUP_LIST: 4203 readGroupList( 4204 message, 4205 offset(typeAndOffset), 4206 reader, 4207 (Schema<T>) getMessageFieldSchema(pos), 4208 extensionRegistry); 4209 break; 4210 } 4211 case 50: // MAP: 4212 mergeMap(message, pos, getMapFieldDefaultEntry(pos), extensionRegistry, reader); 4213 break; 4214 case 51: // ONEOF_DOUBLE: 4215 UnsafeUtil.putObject( 4216 message, offset(typeAndOffset), Double.valueOf(reader.readDouble())); 4217 setOneofPresent(message, number, pos); 4218 break; 4219 case 52: // ONEOF_FLOAT: 4220 UnsafeUtil.putObject( 4221 message, offset(typeAndOffset), Float.valueOf(reader.readFloat())); 4222 setOneofPresent(message, number, pos); 4223 break; 4224 case 53: // ONEOF_INT64: 4225 UnsafeUtil.putObject( 4226 message, offset(typeAndOffset), Long.valueOf(reader.readInt64())); 4227 setOneofPresent(message, number, pos); 4228 break; 4229 case 54: // ONEOF_UINT64: 4230 UnsafeUtil.putObject( 4231 message, offset(typeAndOffset), Long.valueOf(reader.readUInt64())); 4232 setOneofPresent(message, number, pos); 4233 break; 4234 case 55: // ONEOF_INT32: 4235 UnsafeUtil.putObject( 4236 message, offset(typeAndOffset), Integer.valueOf(reader.readInt32())); 4237 setOneofPresent(message, number, pos); 4238 break; 4239 case 56: // ONEOF_FIXED64: 4240 UnsafeUtil.putObject( 4241 message, offset(typeAndOffset), Long.valueOf(reader.readFixed64())); 4242 setOneofPresent(message, number, pos); 4243 break; 4244 case 57: // ONEOF_FIXED32: 4245 UnsafeUtil.putObject( 4246 message, offset(typeAndOffset), Integer.valueOf(reader.readFixed32())); 4247 setOneofPresent(message, number, pos); 4248 break; 4249 case 58: // ONEOF_BOOL: 4250 UnsafeUtil.putObject( 4251 message, offset(typeAndOffset), Boolean.valueOf(reader.readBool())); 4252 setOneofPresent(message, number, pos); 4253 break; 4254 case 59: // ONEOF_STRING: 4255 readString(message, typeAndOffset, reader); 4256 setOneofPresent(message, number, pos); 4257 break; 4258 case 60: 4259 { // ONEOF_MESSAGE: 4260 final MessageLite current = 4261 (MessageLite) mutableOneofMessageFieldForMerge(message, number, pos); 4262 reader.mergeMessageField( 4263 current, (Schema<MessageLite>) getMessageFieldSchema(pos), extensionRegistry); 4264 storeOneofMessageField(message, number, pos, current); 4265 break; 4266 } 4267 case 61: // ONEOF_BYTES: 4268 UnsafeUtil.putObject(message, offset(typeAndOffset), reader.readBytes()); 4269 setOneofPresent(message, number, pos); 4270 break; 4271 case 62: // ONEOF_UINT32: 4272 UnsafeUtil.putObject( 4273 message, offset(typeAndOffset), Integer.valueOf(reader.readUInt32())); 4274 setOneofPresent(message, number, pos); 4275 break; 4276 case 63: // ONEOF_ENUM: 4277 { 4278 int enumValue = reader.readEnum(); 4279 EnumVerifier enumVerifier = getEnumFieldVerifier(pos); 4280 if (enumVerifier == null || enumVerifier.isInRange(enumValue)) { 4281 UnsafeUtil.putObject(message, offset(typeAndOffset), enumValue); 4282 setOneofPresent(message, number, pos); 4283 } else { 4284 unknownFields = 4285 SchemaUtil.storeUnknownEnum( 4286 message, number, enumValue, unknownFields, unknownFieldSchema); 4287 } 4288 break; 4289 } 4290 case 64: // ONEOF_SFIXED32: 4291 UnsafeUtil.putObject( 4292 message, offset(typeAndOffset), Integer.valueOf(reader.readSFixed32())); 4293 setOneofPresent(message, number, pos); 4294 break; 4295 case 65: // ONEOF_SFIXED64: 4296 UnsafeUtil.putObject( 4297 message, offset(typeAndOffset), Long.valueOf(reader.readSFixed64())); 4298 setOneofPresent(message, number, pos); 4299 break; 4300 case 66: // ONEOF_SINT32: 4301 UnsafeUtil.putObject( 4302 message, offset(typeAndOffset), Integer.valueOf(reader.readSInt32())); 4303 setOneofPresent(message, number, pos); 4304 break; 4305 case 67: // ONEOF_SINT64: 4306 UnsafeUtil.putObject( 4307 message, offset(typeAndOffset), Long.valueOf(reader.readSInt64())); 4308 setOneofPresent(message, number, pos); 4309 break; 4310 case 68: 4311 { // ONEOF_GROUP: 4312 final MessageLite current = 4313 (MessageLite) mutableOneofMessageFieldForMerge(message, number, pos); 4314 reader.mergeGroupField( 4315 current, (Schema<MessageLite>) getMessageFieldSchema(pos), extensionRegistry); 4316 storeOneofMessageField(message, number, pos, current); 4317 break; 4318 } 4319 default: 4320 // Assume we've landed on an empty entry. Treat it as an unknown field. 4321 if (unknownFields == null) { 4322 unknownFields = unknownFieldSchema.getBuilderFromMessage(message); 4323 } 4324 if (!unknownFieldSchema.mergeOneFieldFrom(unknownFields, reader)) { 4325 return; 4326 } 4327 break; 4328 } 4329 } catch (InvalidProtocolBufferException.InvalidWireTypeException e) { 4330 // Treat fields with an invalid wire type as unknown fields 4331 // (i.e. same as the default case). 4332 if (unknownFieldSchema.shouldDiscardUnknownFields(reader)) { 4333 if (!reader.skipField()) { 4334 return; 4335 } 4336 } else { 4337 if (unknownFields == null) { 4338 unknownFields = unknownFieldSchema.getBuilderFromMessage(message); 4339 } 4340 if (!unknownFieldSchema.mergeOneFieldFrom(unknownFields, reader)) { 4341 return; 4342 } 4343 } 4344 } 4345 } 4346 } finally { 4347 for (int i = checkInitializedCount; i < repeatedFieldOffsetStart; i++) { 4348 unknownFields = 4349 filterMapUnknownEnumValues( 4350 message, intArray[i], unknownFields, unknownFieldSchema, message); 4351 } 4352 if (unknownFields != null) { 4353 unknownFieldSchema.setBuilderToMessage(message, unknownFields); 4354 } 4355 } 4356 } 4357 4358 @SuppressWarnings("ReferenceEquality") getMutableUnknownFields(Object message)4359 static UnknownFieldSetLite getMutableUnknownFields(Object message) { 4360 // TODO(b/248560713) decide if we're keeping support for Full in schema classes and handle this 4361 // better. 4362 UnknownFieldSetLite unknownFields = ((GeneratedMessageLite) message).unknownFields; 4363 if (unknownFields == UnknownFieldSetLite.getDefaultInstance()) { 4364 unknownFields = UnknownFieldSetLite.newInstance(); 4365 ((GeneratedMessageLite) message).unknownFields = unknownFields; 4366 } 4367 return unknownFields; 4368 } 4369 4370 /** Decodes a map entry key or value. Stores result in registers.object1. */ decodeMapEntryValue( byte[] data, int position, int limit, WireFormat.FieldType fieldType, Class<?> messageType, Registers registers)4371 private int decodeMapEntryValue( 4372 byte[] data, 4373 int position, 4374 int limit, 4375 WireFormat.FieldType fieldType, 4376 Class<?> messageType, 4377 Registers registers) 4378 throws IOException { 4379 switch (fieldType) { 4380 case BOOL: 4381 position = decodeVarint64(data, position, registers); 4382 registers.object1 = registers.long1 != 0; 4383 break; 4384 case BYTES: 4385 position = decodeBytes(data, position, registers); 4386 break; 4387 case DOUBLE: 4388 registers.object1 = decodeDouble(data, position); 4389 position += 8; 4390 break; 4391 case FIXED32: 4392 case SFIXED32: 4393 registers.object1 = decodeFixed32(data, position); 4394 position += 4; 4395 break; 4396 case FIXED64: 4397 case SFIXED64: 4398 registers.object1 = decodeFixed64(data, position); 4399 position += 8; 4400 break; 4401 case FLOAT: 4402 registers.object1 = decodeFloat(data, position); 4403 position += 4; 4404 break; 4405 case ENUM: 4406 case INT32: 4407 case UINT32: 4408 position = decodeVarint32(data, position, registers); 4409 registers.object1 = registers.int1; 4410 break; 4411 case INT64: 4412 case UINT64: 4413 position = decodeVarint64(data, position, registers); 4414 registers.object1 = registers.long1; 4415 break; 4416 case MESSAGE: 4417 position = 4418 decodeMessageField( 4419 Protobuf.getInstance().schemaFor(messageType), data, position, limit, registers); 4420 break; 4421 case SINT32: 4422 position = decodeVarint32(data, position, registers); 4423 registers.object1 = CodedInputStream.decodeZigZag32(registers.int1); 4424 break; 4425 case SINT64: 4426 position = decodeVarint64(data, position, registers); 4427 registers.object1 = CodedInputStream.decodeZigZag64(registers.long1); 4428 break; 4429 case STRING: 4430 position = decodeStringRequireUtf8(data, position, registers); 4431 break; 4432 default: 4433 throw new RuntimeException("unsupported field type."); 4434 } 4435 return position; 4436 } 4437 4438 /** Decodes a map entry. */ decodeMapEntry( byte[] data, int position, int limit, MapEntryLite.Metadata<K, V> metadata, Map<K, V> target, Registers registers)4439 private <K, V> int decodeMapEntry( 4440 byte[] data, 4441 int position, 4442 int limit, 4443 MapEntryLite.Metadata<K, V> metadata, 4444 Map<K, V> target, 4445 Registers registers) 4446 throws IOException { 4447 position = decodeVarint32(data, position, registers); 4448 final int length = registers.int1; 4449 if (length < 0 || length > limit - position) { 4450 throw InvalidProtocolBufferException.truncatedMessage(); 4451 } 4452 final int end = position + length; 4453 K key = metadata.defaultKey; 4454 V value = metadata.defaultValue; 4455 while (position < end) { 4456 int tag = data[position++]; 4457 if (tag < 0) { 4458 position = decodeVarint32(tag, data, position, registers); 4459 tag = registers.int1; 4460 } 4461 final int fieldNumber = tag >>> 3; 4462 final int wireType = tag & 0x7; 4463 switch (fieldNumber) { 4464 case 1: 4465 if (wireType == metadata.keyType.getWireType()) { 4466 position = 4467 decodeMapEntryValue(data, position, limit, metadata.keyType, null, registers); 4468 key = (K) registers.object1; 4469 continue; 4470 } 4471 break; 4472 case 2: 4473 if (wireType == metadata.valueType.getWireType()) { 4474 position = 4475 decodeMapEntryValue( 4476 data, 4477 position, 4478 limit, 4479 metadata.valueType, 4480 metadata.defaultValue.getClass(), 4481 registers); 4482 value = (V) registers.object1; 4483 continue; 4484 } 4485 break; 4486 default: 4487 break; 4488 } 4489 position = skipField(tag, data, position, limit, registers); 4490 } 4491 if (position != end) { 4492 throw InvalidProtocolBufferException.parseFailure(); 4493 } 4494 target.put(key, value); 4495 return end; 4496 } 4497 4498 @SuppressWarnings("ReferenceEquality") parseRepeatedField( T message, byte[] data, int position, int limit, int tag, int number, int wireType, int bufferPosition, long typeAndOffset, int fieldType, long fieldOffset, Registers registers)4499 private int parseRepeatedField( 4500 T message, 4501 byte[] data, 4502 int position, 4503 int limit, 4504 int tag, 4505 int number, 4506 int wireType, 4507 int bufferPosition, 4508 long typeAndOffset, 4509 int fieldType, 4510 long fieldOffset, 4511 Registers registers) 4512 throws IOException { 4513 ProtobufList<?> list = (ProtobufList<?>) UNSAFE.getObject(message, fieldOffset); 4514 if (!list.isModifiable()) { 4515 final int size = list.size(); 4516 list = 4517 list.mutableCopyWithCapacity( 4518 size == 0 ? AbstractProtobufList.DEFAULT_CAPACITY : size * 2); 4519 UNSAFE.putObject(message, fieldOffset, list); 4520 } 4521 switch (fieldType) { 4522 case 18: // DOUBLE_LIST: 4523 case 35: // DOUBLE_LIST_PACKED: 4524 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4525 position = decodePackedDoubleList(data, position, list, registers); 4526 } else if (wireType == WireFormat.WIRETYPE_FIXED64) { 4527 position = decodeDoubleList(tag, data, position, limit, list, registers); 4528 } 4529 break; 4530 case 19: // FLOAT_LIST: 4531 case 36: // FLOAT_LIST_PACKED: 4532 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4533 position = decodePackedFloatList(data, position, list, registers); 4534 } else if (wireType == WireFormat.WIRETYPE_FIXED32) { 4535 position = decodeFloatList(tag, data, position, limit, list, registers); 4536 } 4537 break; 4538 case 20: // INT64_LIST: 4539 case 21: // UINT64_LIST: 4540 case 37: // INT64_LIST_PACKED: 4541 case 38: // UINT64_LIST_PACKED: 4542 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4543 position = decodePackedVarint64List(data, position, list, registers); 4544 } else if (wireType == WireFormat.WIRETYPE_VARINT) { 4545 position = decodeVarint64List(tag, data, position, limit, list, registers); 4546 } 4547 break; 4548 case 22: // INT32_LIST: 4549 case 29: // UINT32_LIST: 4550 case 39: // INT32_LIST_PACKED: 4551 case 43: // UINT32_LIST_PACKED: 4552 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4553 position = decodePackedVarint32List(data, position, list, registers); 4554 } else if (wireType == WireFormat.WIRETYPE_VARINT) { 4555 position = decodeVarint32List(tag, data, position, limit, list, registers); 4556 } 4557 break; 4558 case 23: // FIXED64_LIST: 4559 case 32: // SFIXED64_LIST: 4560 case 40: // FIXED64_LIST_PACKED: 4561 case 46: // SFIXED64_LIST_PACKED: 4562 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4563 position = decodePackedFixed64List(data, position, list, registers); 4564 } else if (wireType == WireFormat.WIRETYPE_FIXED64) { 4565 position = decodeFixed64List(tag, data, position, limit, list, registers); 4566 } 4567 break; 4568 case 24: // FIXED32_LIST: 4569 case 31: // SFIXED32_LIST: 4570 case 41: // FIXED32_LIST_PACKED: 4571 case 45: // SFIXED32_LIST_PACKED: 4572 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4573 position = decodePackedFixed32List(data, position, list, registers); 4574 } else if (wireType == WireFormat.WIRETYPE_FIXED32) { 4575 position = decodeFixed32List(tag, data, position, limit, list, registers); 4576 } 4577 break; 4578 case 25: // BOOL_LIST: 4579 case 42: // BOOL_LIST_PACKED: 4580 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4581 position = decodePackedBoolList(data, position, list, registers); 4582 } else if (wireType == WireFormat.WIRETYPE_VARINT) { 4583 position = decodeBoolList(tag, data, position, limit, list, registers); 4584 } 4585 break; 4586 case 26: // STRING_LIST: 4587 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4588 if ((typeAndOffset & ENFORCE_UTF8_MASK) == 0) { 4589 position = decodeStringList(tag, data, position, limit, list, registers); 4590 } else { 4591 position = decodeStringListRequireUtf8(tag, data, position, limit, list, registers); 4592 } 4593 } 4594 break; 4595 case 27: // MESSAGE_LIST: 4596 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4597 position = 4598 decodeMessageList( 4599 getMessageFieldSchema(bufferPosition), 4600 tag, 4601 data, 4602 position, 4603 limit, 4604 list, 4605 registers); 4606 } 4607 break; 4608 case 28: // BYTES_LIST: 4609 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4610 position = decodeBytesList(tag, data, position, limit, list, registers); 4611 } 4612 break; 4613 case 30: // ENUM_LIST: 4614 case 44: // ENUM_LIST_PACKED: 4615 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4616 position = decodePackedVarint32List(data, position, list, registers); 4617 } else if (wireType == WireFormat.WIRETYPE_VARINT) { 4618 position = decodeVarint32List(tag, data, position, limit, list, registers); 4619 } else { 4620 break; 4621 } 4622 SchemaUtil.filterUnknownEnumList( 4623 message, 4624 number, 4625 (ProtobufList<Integer>) list, 4626 getEnumFieldVerifier(bufferPosition), 4627 null, 4628 (UnknownFieldSchema<UnknownFieldSetLite, UnknownFieldSetLite>) unknownFieldSchema); 4629 break; 4630 case 33: // SINT32_LIST: 4631 case 47: // SINT32_LIST_PACKED: 4632 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4633 position = decodePackedSInt32List(data, position, list, registers); 4634 } else if (wireType == WireFormat.WIRETYPE_VARINT) { 4635 position = decodeSInt32List(tag, data, position, limit, list, registers); 4636 } 4637 break; 4638 case 34: // SINT64_LIST: 4639 case 48: // SINT64_LIST_PACKED: 4640 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4641 position = decodePackedSInt64List(data, position, list, registers); 4642 } else if (wireType == WireFormat.WIRETYPE_VARINT) { 4643 position = decodeSInt64List(tag, data, position, limit, list, registers); 4644 } 4645 break; 4646 case 49: // GROUP_LIST: 4647 if (wireType == WireFormat.WIRETYPE_START_GROUP) { 4648 position = 4649 decodeGroupList( 4650 getMessageFieldSchema(bufferPosition), 4651 tag, 4652 data, 4653 position, 4654 limit, 4655 list, 4656 registers); 4657 } 4658 break; 4659 default: 4660 break; 4661 } 4662 return position; 4663 } 4664 parseMapField( T message, byte[] data, int position, int limit, int bufferPosition, long fieldOffset, Registers registers)4665 private <K, V> int parseMapField( 4666 T message, 4667 byte[] data, 4668 int position, 4669 int limit, 4670 int bufferPosition, 4671 long fieldOffset, 4672 Registers registers) 4673 throws IOException { 4674 final sun.misc.Unsafe unsafe = UNSAFE; 4675 Object mapDefaultEntry = getMapFieldDefaultEntry(bufferPosition); 4676 Object mapField = unsafe.getObject(message, fieldOffset); 4677 if (mapFieldSchema.isImmutable(mapField)) { 4678 Object oldMapField = mapField; 4679 mapField = mapFieldSchema.newMapField(mapDefaultEntry); 4680 mapFieldSchema.mergeFrom(mapField, oldMapField); 4681 unsafe.putObject(message, fieldOffset, mapField); 4682 } 4683 return decodeMapEntry( 4684 data, 4685 position, 4686 limit, 4687 (Metadata<K, V>) mapFieldSchema.forMapMetadata(mapDefaultEntry), 4688 (Map<K, V>) mapFieldSchema.forMutableMapData(mapField), 4689 registers); 4690 } 4691 parseOneofField( T message, byte[] data, int position, int limit, int tag, int number, int wireType, int typeAndOffset, int fieldType, long fieldOffset, int bufferPosition, Registers registers)4692 private int parseOneofField( 4693 T message, 4694 byte[] data, 4695 int position, 4696 int limit, 4697 int tag, 4698 int number, 4699 int wireType, 4700 int typeAndOffset, 4701 int fieldType, 4702 long fieldOffset, 4703 int bufferPosition, 4704 Registers registers) 4705 throws IOException { 4706 final sun.misc.Unsafe unsafe = UNSAFE; 4707 final long oneofCaseOffset = buffer[bufferPosition + 2] & OFFSET_MASK; 4708 switch (fieldType) { 4709 case 51: // ONEOF_DOUBLE: 4710 if (wireType == WireFormat.WIRETYPE_FIXED64) { 4711 unsafe.putObject(message, fieldOffset, decodeDouble(data, position)); 4712 position += 8; 4713 unsafe.putInt(message, oneofCaseOffset, number); 4714 } 4715 break; 4716 case 52: // ONEOF_FLOAT: 4717 if (wireType == WireFormat.WIRETYPE_FIXED32) { 4718 unsafe.putObject(message, fieldOffset, decodeFloat(data, position)); 4719 position += 4; 4720 unsafe.putInt(message, oneofCaseOffset, number); 4721 } 4722 break; 4723 case 53: // ONEOF_INT64: 4724 case 54: // ONEOF_UINT64: 4725 if (wireType == WireFormat.WIRETYPE_VARINT) { 4726 position = decodeVarint64(data, position, registers); 4727 unsafe.putObject(message, fieldOffset, registers.long1); 4728 unsafe.putInt(message, oneofCaseOffset, number); 4729 } 4730 break; 4731 case 55: // ONEOF_INT32: 4732 case 62: // ONEOF_UINT32: 4733 if (wireType == WireFormat.WIRETYPE_VARINT) { 4734 position = decodeVarint32(data, position, registers); 4735 unsafe.putObject(message, fieldOffset, registers.int1); 4736 unsafe.putInt(message, oneofCaseOffset, number); 4737 } 4738 break; 4739 case 56: // ONEOF_FIXED64: 4740 case 65: // ONEOF_SFIXED64: 4741 if (wireType == WireFormat.WIRETYPE_FIXED64) { 4742 unsafe.putObject(message, fieldOffset, decodeFixed64(data, position)); 4743 position += 8; 4744 unsafe.putInt(message, oneofCaseOffset, number); 4745 } 4746 break; 4747 case 57: // ONEOF_FIXED32: 4748 case 64: // ONEOF_SFIXED32: 4749 if (wireType == WireFormat.WIRETYPE_FIXED32) { 4750 unsafe.putObject(message, fieldOffset, decodeFixed32(data, position)); 4751 position += 4; 4752 unsafe.putInt(message, oneofCaseOffset, number); 4753 } 4754 break; 4755 case 58: // ONEOF_BOOL: 4756 if (wireType == WireFormat.WIRETYPE_VARINT) { 4757 position = decodeVarint64(data, position, registers); 4758 unsafe.putObject(message, fieldOffset, registers.long1 != 0); 4759 unsafe.putInt(message, oneofCaseOffset, number); 4760 } 4761 break; 4762 case 59: // ONEOF_STRING: 4763 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4764 position = decodeVarint32(data, position, registers); 4765 final int length = registers.int1; 4766 if (length == 0) { 4767 unsafe.putObject(message, fieldOffset, ""); 4768 } else { 4769 if ((typeAndOffset & ENFORCE_UTF8_MASK) != 0 4770 && !Utf8.isValidUtf8(data, position, position + length)) { 4771 throw InvalidProtocolBufferException.invalidUtf8(); 4772 } 4773 final String value = new String(data, position, length, Internal.UTF_8); 4774 unsafe.putObject(message, fieldOffset, value); 4775 position += length; 4776 } 4777 unsafe.putInt(message, oneofCaseOffset, number); 4778 } 4779 break; 4780 case 60: // ONEOF_MESSAGE: 4781 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4782 final Object current = mutableOneofMessageFieldForMerge(message, number, bufferPosition); 4783 position = 4784 mergeMessageField( 4785 current, getMessageFieldSchema(bufferPosition), data, position, limit, registers); 4786 storeOneofMessageField(message, number, bufferPosition, current); 4787 } 4788 break; 4789 case 61: // ONEOF_BYTES: 4790 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4791 position = decodeBytes(data, position, registers); 4792 unsafe.putObject(message, fieldOffset, registers.object1); 4793 unsafe.putInt(message, oneofCaseOffset, number); 4794 } 4795 break; 4796 case 63: // ONEOF_ENUM: 4797 if (wireType == WireFormat.WIRETYPE_VARINT) { 4798 position = decodeVarint32(data, position, registers); 4799 final int enumValue = registers.int1; 4800 EnumVerifier enumVerifier = getEnumFieldVerifier(bufferPosition); 4801 if (enumVerifier == null || enumVerifier.isInRange(enumValue)) { 4802 unsafe.putObject(message, fieldOffset, enumValue); 4803 unsafe.putInt(message, oneofCaseOffset, number); 4804 } else { 4805 // UnknownFieldSetLite requires varint to be represented as Long. 4806 getMutableUnknownFields(message).storeField(tag, (long) enumValue); 4807 } 4808 } 4809 break; 4810 case 66: // ONEOF_SINT32: 4811 if (wireType == WireFormat.WIRETYPE_VARINT) { 4812 position = decodeVarint32(data, position, registers); 4813 unsafe.putObject(message, fieldOffset, CodedInputStream.decodeZigZag32(registers.int1)); 4814 unsafe.putInt(message, oneofCaseOffset, number); 4815 } 4816 break; 4817 case 67: // ONEOF_SINT64: 4818 if (wireType == WireFormat.WIRETYPE_VARINT) { 4819 position = decodeVarint64(data, position, registers); 4820 unsafe.putObject(message, fieldOffset, CodedInputStream.decodeZigZag64(registers.long1)); 4821 unsafe.putInt(message, oneofCaseOffset, number); 4822 } 4823 break; 4824 case 68: // ONEOF_GROUP: 4825 if (wireType == WireFormat.WIRETYPE_START_GROUP) { 4826 final Object current = mutableOneofMessageFieldForMerge(message, number, bufferPosition); 4827 final int endTag = (tag & ~0x7) | WireFormat.WIRETYPE_END_GROUP; 4828 position = 4829 mergeGroupField( 4830 current, 4831 getMessageFieldSchema(bufferPosition), 4832 data, 4833 position, 4834 limit, 4835 endTag, 4836 registers); 4837 storeOneofMessageField(message, number, bufferPosition, current); 4838 } 4839 break; 4840 default: 4841 break; 4842 } 4843 return position; 4844 } 4845 getMessageFieldSchema(int pos)4846 private Schema getMessageFieldSchema(int pos) { 4847 final int index = pos / INTS_PER_FIELD * 2; 4848 Schema schema = (Schema) objects[index]; 4849 if (schema != null) { 4850 return schema; 4851 } 4852 schema = Protobuf.getInstance().schemaFor((Class) objects[index + 1]); 4853 objects[index] = schema; 4854 return schema; 4855 } 4856 getMapFieldDefaultEntry(int pos)4857 private Object getMapFieldDefaultEntry(int pos) { 4858 return objects[pos / INTS_PER_FIELD * 2]; 4859 } 4860 getEnumFieldVerifier(int pos)4861 private EnumVerifier getEnumFieldVerifier(int pos) { 4862 return (EnumVerifier) objects[pos / INTS_PER_FIELD * 2 + 1]; 4863 } 4864 4865 /** 4866 * Parses a proto2 message or group and returns the position after the message/group. If it's 4867 * parsing a message (endGroup == 0), returns limit if parsing is successful; It it's parsing a 4868 * group (endGroup != 0), parsing ends when a tag == endGroup is encountered and the position 4869 * after that tag is returned. 4870 */ parseProto2Message( T message, byte[] data, int position, int limit, int endGroup, Registers registers)4871 int parseProto2Message( 4872 T message, byte[] data, int position, int limit, int endGroup, Registers registers) 4873 throws IOException { 4874 checkMutable(message); 4875 final sun.misc.Unsafe unsafe = UNSAFE; 4876 int currentPresenceFieldOffset = NO_PRESENCE_SENTINEL; 4877 int currentPresenceField = 0; 4878 int tag = 0; 4879 int oldNumber = -1; 4880 int pos = 0; 4881 while (position < limit) { 4882 tag = data[position++]; 4883 if (tag < 0) { 4884 position = decodeVarint32(tag, data, position, registers); 4885 tag = registers.int1; 4886 } 4887 final int number = tag >>> 3; 4888 final int wireType = tag & 0x7; 4889 if (number > oldNumber) { 4890 pos = positionForFieldNumber(number, pos / INTS_PER_FIELD); 4891 } else { 4892 pos = positionForFieldNumber(number); 4893 } 4894 oldNumber = number; 4895 if (pos == -1) { 4896 // need to reset 4897 pos = 0; 4898 } else { 4899 final int typeAndOffset = buffer[pos + 1]; 4900 final int fieldType = type(typeAndOffset); 4901 final long fieldOffset = offset(typeAndOffset); 4902 if (fieldType <= 17) { 4903 // Proto2 optional fields have has-bits. 4904 final int presenceMaskAndOffset = buffer[pos + 2]; 4905 final int presenceMask = 1 << (presenceMaskAndOffset >>> OFFSET_BITS); 4906 final int presenceFieldOffset = presenceMaskAndOffset & OFFSET_MASK; 4907 // We cache the 32-bit has-bits integer value and only write it back when parsing a field 4908 // using a different has-bits integer. 4909 if (presenceFieldOffset != currentPresenceFieldOffset) { 4910 if (currentPresenceFieldOffset != NO_PRESENCE_SENTINEL) { 4911 unsafe.putInt(message, (long) currentPresenceFieldOffset, currentPresenceField); 4912 } 4913 currentPresenceFieldOffset = presenceFieldOffset; 4914 currentPresenceField = unsafe.getInt(message, (long) presenceFieldOffset); 4915 } 4916 switch (fieldType) { 4917 case 0: // DOUBLE 4918 if (wireType == WireFormat.WIRETYPE_FIXED64) { 4919 UnsafeUtil.putDouble(message, fieldOffset, decodeDouble(data, position)); 4920 position += 8; 4921 currentPresenceField |= presenceMask; 4922 continue; 4923 } 4924 break; 4925 case 1: // FLOAT 4926 if (wireType == WireFormat.WIRETYPE_FIXED32) { 4927 UnsafeUtil.putFloat(message, fieldOffset, decodeFloat(data, position)); 4928 position += 4; 4929 currentPresenceField |= presenceMask; 4930 continue; 4931 } 4932 break; 4933 case 2: // INT64 4934 case 3: // UINT64 4935 if (wireType == WireFormat.WIRETYPE_VARINT) { 4936 position = decodeVarint64(data, position, registers); 4937 unsafe.putLong(message, fieldOffset, registers.long1); 4938 currentPresenceField |= presenceMask; 4939 continue; 4940 } 4941 break; 4942 case 4: // INT32 4943 case 11: // UINT32 4944 if (wireType == WireFormat.WIRETYPE_VARINT) { 4945 position = decodeVarint32(data, position, registers); 4946 unsafe.putInt(message, fieldOffset, registers.int1); 4947 currentPresenceField |= presenceMask; 4948 continue; 4949 } 4950 break; 4951 case 5: // FIXED64 4952 case 14: // SFIXED64 4953 if (wireType == WireFormat.WIRETYPE_FIXED64) { 4954 unsafe.putLong(message, fieldOffset, decodeFixed64(data, position)); 4955 position += 8; 4956 currentPresenceField |= presenceMask; 4957 continue; 4958 } 4959 break; 4960 case 6: // FIXED32 4961 case 13: // SFIXED32 4962 if (wireType == WireFormat.WIRETYPE_FIXED32) { 4963 unsafe.putInt(message, fieldOffset, decodeFixed32(data, position)); 4964 position += 4; 4965 currentPresenceField |= presenceMask; 4966 continue; 4967 } 4968 break; 4969 case 7: // BOOL 4970 if (wireType == WireFormat.WIRETYPE_VARINT) { 4971 position = decodeVarint64(data, position, registers); 4972 UnsafeUtil.putBoolean(message, fieldOffset, registers.long1 != 0); 4973 currentPresenceField |= presenceMask; 4974 continue; 4975 } 4976 break; 4977 case 8: // STRING 4978 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4979 if ((typeAndOffset & ENFORCE_UTF8_MASK) == 0) { 4980 position = decodeString(data, position, registers); 4981 } else { 4982 position = decodeStringRequireUtf8(data, position, registers); 4983 } 4984 unsafe.putObject(message, fieldOffset, registers.object1); 4985 currentPresenceField |= presenceMask; 4986 continue; 4987 } 4988 break; 4989 case 9: // MESSAGE 4990 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 4991 final Object current = mutableMessageFieldForMerge(message, pos); 4992 position = 4993 mergeMessageField( 4994 current, getMessageFieldSchema(pos), data, position, limit, registers); 4995 storeMessageField(message, pos, current); 4996 currentPresenceField |= presenceMask; 4997 continue; 4998 } 4999 break; 5000 case 10: // BYTES 5001 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 5002 position = decodeBytes(data, position, registers); 5003 unsafe.putObject(message, fieldOffset, registers.object1); 5004 currentPresenceField |= presenceMask; 5005 continue; 5006 } 5007 break; 5008 case 12: // ENUM 5009 if (wireType == WireFormat.WIRETYPE_VARINT) { 5010 position = decodeVarint32(data, position, registers); 5011 final int enumValue = registers.int1; 5012 EnumVerifier enumVerifier = getEnumFieldVerifier(pos); 5013 if (enumVerifier == null || enumVerifier.isInRange(enumValue)) { 5014 unsafe.putInt(message, fieldOffset, enumValue); 5015 currentPresenceField |= presenceMask; 5016 } else { 5017 // UnknownFieldSetLite requires varint to be represented as Long. 5018 getMutableUnknownFields(message).storeField(tag, (long) enumValue); 5019 } 5020 continue; 5021 } 5022 break; 5023 case 15: // SINT32 5024 if (wireType == WireFormat.WIRETYPE_VARINT) { 5025 position = decodeVarint32(data, position, registers); 5026 unsafe.putInt( 5027 message, fieldOffset, CodedInputStream.decodeZigZag32(registers.int1)); 5028 currentPresenceField |= presenceMask; 5029 continue; 5030 } 5031 break; 5032 case 16: // SINT64 5033 if (wireType == WireFormat.WIRETYPE_VARINT) { 5034 position = decodeVarint64(data, position, registers); 5035 unsafe.putLong( 5036 message, fieldOffset, CodedInputStream.decodeZigZag64(registers.long1)); 5037 5038 currentPresenceField |= presenceMask; 5039 continue; 5040 } 5041 break; 5042 case 17: // GROUP 5043 if (wireType == WireFormat.WIRETYPE_START_GROUP) { 5044 final Object current = mutableMessageFieldForMerge(message, pos); 5045 final int endTag = (number << 3) | WireFormat.WIRETYPE_END_GROUP; 5046 position = 5047 mergeGroupField( 5048 current, 5049 getMessageFieldSchema(pos), 5050 data, 5051 position, 5052 limit, 5053 endTag, 5054 registers); 5055 storeMessageField(message, pos, current); 5056 currentPresenceField |= presenceMask; 5057 continue; 5058 } 5059 break; 5060 default: 5061 break; 5062 } 5063 } else if (fieldType == 27) { 5064 // Handle repeated message fields. 5065 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 5066 ProtobufList<?> list = (ProtobufList<?>) unsafe.getObject(message, fieldOffset); 5067 if (!list.isModifiable()) { 5068 final int size = list.size(); 5069 list = 5070 list.mutableCopyWithCapacity( 5071 size == 0 ? AbstractProtobufList.DEFAULT_CAPACITY : size * 2); 5072 unsafe.putObject(message, fieldOffset, list); 5073 } 5074 position = 5075 decodeMessageList( 5076 getMessageFieldSchema(pos), tag, data, position, limit, list, registers); 5077 continue; 5078 } 5079 } else if (fieldType <= 49) { 5080 // Handle all other repeated fields. 5081 final int oldPosition = position; 5082 position = 5083 parseRepeatedField( 5084 message, 5085 data, 5086 position, 5087 limit, 5088 tag, 5089 number, 5090 wireType, 5091 pos, 5092 typeAndOffset, 5093 fieldType, 5094 fieldOffset, 5095 registers); 5096 if (position != oldPosition) { 5097 continue; 5098 } 5099 } else if (fieldType == 50) { 5100 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 5101 final int oldPosition = position; 5102 position = parseMapField(message, data, position, limit, pos, fieldOffset, registers); 5103 if (position != oldPosition) { 5104 continue; 5105 } 5106 } 5107 } else { 5108 final int oldPosition = position; 5109 position = 5110 parseOneofField( 5111 message, 5112 data, 5113 position, 5114 limit, 5115 tag, 5116 number, 5117 wireType, 5118 typeAndOffset, 5119 fieldType, 5120 fieldOffset, 5121 pos, 5122 registers); 5123 if (position != oldPosition) { 5124 continue; 5125 } 5126 } 5127 } 5128 if (tag == endGroup && endGroup != 0) { 5129 break; 5130 } 5131 5132 if (hasExtensions 5133 && registers.extensionRegistry != ExtensionRegistryLite.getEmptyRegistry()) { 5134 position = decodeExtensionOrUnknownField( 5135 tag, data, position, limit, message, defaultInstance, 5136 (UnknownFieldSchema<UnknownFieldSetLite, UnknownFieldSetLite>) unknownFieldSchema, 5137 registers); 5138 } else { 5139 position = decodeUnknownField( 5140 tag, data, position, limit, getMutableUnknownFields(message), registers); 5141 } 5142 } 5143 if (currentPresenceFieldOffset != NO_PRESENCE_SENTINEL) { 5144 unsafe.putInt(message, (long) currentPresenceFieldOffset, currentPresenceField); 5145 } 5146 UnknownFieldSetLite unknownFields = null; 5147 for (int i = checkInitializedCount; i < repeatedFieldOffsetStart; i++) { 5148 unknownFields = 5149 filterMapUnknownEnumValues( 5150 message, 5151 intArray[i], 5152 unknownFields, 5153 (UnknownFieldSchema<UnknownFieldSetLite, UnknownFieldSetLite>) unknownFieldSchema, 5154 message); 5155 } 5156 if (unknownFields != null) { 5157 ((UnknownFieldSchema<UnknownFieldSetLite, UnknownFieldSetLite>) unknownFieldSchema) 5158 .setBuilderToMessage(message, unknownFields); 5159 } 5160 if (endGroup == 0) { 5161 if (position != limit) { 5162 throw InvalidProtocolBufferException.parseFailure(); 5163 } 5164 } else { 5165 if (position > limit || tag != endGroup) { 5166 throw InvalidProtocolBufferException.parseFailure(); 5167 } 5168 } 5169 return position; 5170 } 5171 mutableMessageFieldForMerge(T message, int pos)5172 private Object mutableMessageFieldForMerge(T message, int pos) { 5173 final Schema fieldSchema = getMessageFieldSchema(pos); 5174 final long offset = offset(typeAndOffsetAt(pos)); 5175 5176 // Field not present, create a new one 5177 if (!isFieldPresent(message, pos)) { 5178 return fieldSchema.newInstance(); 5179 } 5180 5181 // Field present, if mutable, ready to merge 5182 final Object current = UNSAFE.getObject(message, offset); 5183 if (isMutable(current)) { 5184 return current; 5185 } 5186 5187 // Field present but immutable, make a new mutable copy 5188 final Object newMessage = fieldSchema.newInstance(); 5189 if (current != null) { 5190 fieldSchema.mergeFrom(newMessage, current); 5191 } 5192 return newMessage; 5193 } 5194 storeMessageField(T message, int pos, Object field)5195 private void storeMessageField(T message, int pos, Object field) { 5196 UNSAFE.putObject(message, offset(typeAndOffsetAt(pos)), field); 5197 setFieldPresent(message, pos); 5198 } 5199 mutableOneofMessageFieldForMerge(T message, int fieldNumber, int pos)5200 private Object mutableOneofMessageFieldForMerge(T message, int fieldNumber, int pos) { 5201 final Schema fieldSchema = getMessageFieldSchema(pos); 5202 5203 // Field not present, create it and mark it present 5204 if (!isOneofPresent(message, fieldNumber, pos)) { 5205 return fieldSchema.newInstance(); 5206 } 5207 5208 // Field present, if mutable, ready to merge 5209 final Object current = UNSAFE.getObject(message, offset(typeAndOffsetAt(pos))); 5210 if (isMutable(current)) { 5211 return current; 5212 } 5213 5214 // Field present but immutable, make a new mutable copy 5215 final Object newMessage = fieldSchema.newInstance(); 5216 if (current != null) { 5217 fieldSchema.mergeFrom(newMessage, current); 5218 } 5219 return newMessage; 5220 } 5221 storeOneofMessageField(T message, int fieldNumber, int pos, Object field)5222 private void storeOneofMessageField(T message, int fieldNumber, int pos, Object field) { 5223 UNSAFE.putObject(message, offset(typeAndOffsetAt(pos)), field); 5224 setOneofPresent(message, fieldNumber, pos); 5225 } 5226 5227 /** Parses a proto3 message and returns the limit if parsing is successful. */ parseProto3Message( T message, byte[] data, int position, int limit, Registers registers)5228 private int parseProto3Message( 5229 T message, byte[] data, int position, int limit, Registers registers) throws IOException { 5230 checkMutable(message); 5231 final sun.misc.Unsafe unsafe = UNSAFE; 5232 int currentPresenceFieldOffset = NO_PRESENCE_SENTINEL; 5233 int currentPresenceField = 0; 5234 int tag = 0; 5235 int oldNumber = -1; 5236 int pos = 0; 5237 while (position < limit) { 5238 tag = data[position++]; 5239 if (tag < 0) { 5240 position = decodeVarint32(tag, data, position, registers); 5241 tag = registers.int1; 5242 } 5243 final int number = tag >>> 3; 5244 final int wireType = tag & 0x7; 5245 if (number > oldNumber) { 5246 pos = positionForFieldNumber(number, pos / INTS_PER_FIELD); 5247 } else { 5248 pos = positionForFieldNumber(number); 5249 } 5250 oldNumber = number; 5251 if (pos == -1) { 5252 // need to reset 5253 pos = 0; 5254 } else { 5255 final int typeAndOffset = buffer[pos + 1]; 5256 final int fieldType = type(typeAndOffset); 5257 final long fieldOffset = offset(typeAndOffset); 5258 if (fieldType <= 17) { 5259 // Proto3 optional fields have has-bits. 5260 final int presenceMaskAndOffset = buffer[pos + 2]; 5261 final int presenceMask = 1 << (presenceMaskAndOffset >>> OFFSET_BITS); 5262 final int presenceFieldOffset = presenceMaskAndOffset & OFFSET_MASK; 5263 // We cache the 32-bit has-bits integer value and only write it back when parsing a field 5264 // using a different has-bits integer. 5265 // 5266 // Note that for fields that do not have hasbits, we unconditionally write and discard 5267 // the data. 5268 if (presenceFieldOffset != currentPresenceFieldOffset) { 5269 if (currentPresenceFieldOffset != NO_PRESENCE_SENTINEL) { 5270 unsafe.putInt(message, (long) currentPresenceFieldOffset, currentPresenceField); 5271 } 5272 if (presenceFieldOffset != NO_PRESENCE_SENTINEL) { 5273 currentPresenceField = unsafe.getInt(message, (long) presenceFieldOffset); 5274 } 5275 currentPresenceFieldOffset = presenceFieldOffset; 5276 } 5277 switch (fieldType) { 5278 case 0: // DOUBLE: 5279 if (wireType == WireFormat.WIRETYPE_FIXED64) { 5280 UnsafeUtil.putDouble(message, fieldOffset, decodeDouble(data, position)); 5281 position += 8; 5282 currentPresenceField |= presenceMask; 5283 continue; 5284 } 5285 break; 5286 case 1: // FLOAT: 5287 if (wireType == WireFormat.WIRETYPE_FIXED32) { 5288 UnsafeUtil.putFloat(message, fieldOffset, decodeFloat(data, position)); 5289 position += 4; 5290 currentPresenceField |= presenceMask; 5291 continue; 5292 } 5293 break; 5294 case 2: // INT64: 5295 case 3: // UINT64: 5296 if (wireType == WireFormat.WIRETYPE_VARINT) { 5297 position = decodeVarint64(data, position, registers); 5298 unsafe.putLong(message, fieldOffset, registers.long1); 5299 currentPresenceField |= presenceMask; 5300 continue; 5301 } 5302 break; 5303 case 4: // INT32: 5304 case 11: // UINT32: 5305 if (wireType == WireFormat.WIRETYPE_VARINT) { 5306 position = decodeVarint32(data, position, registers); 5307 unsafe.putInt(message, fieldOffset, registers.int1); 5308 currentPresenceField |= presenceMask; 5309 continue; 5310 } 5311 break; 5312 case 5: // FIXED64: 5313 case 14: // SFIXED64: 5314 if (wireType == WireFormat.WIRETYPE_FIXED64) { 5315 unsafe.putLong(message, fieldOffset, decodeFixed64(data, position)); 5316 position += 8; 5317 currentPresenceField |= presenceMask; 5318 continue; 5319 } 5320 break; 5321 case 6: // FIXED32: 5322 case 13: // SFIXED32: 5323 if (wireType == WireFormat.WIRETYPE_FIXED32) { 5324 unsafe.putInt(message, fieldOffset, decodeFixed32(data, position)); 5325 position += 4; 5326 currentPresenceField |= presenceMask; 5327 continue; 5328 } 5329 break; 5330 case 7: // BOOL: 5331 if (wireType == WireFormat.WIRETYPE_VARINT) { 5332 position = decodeVarint64(data, position, registers); 5333 UnsafeUtil.putBoolean(message, fieldOffset, registers.long1 != 0); 5334 currentPresenceField |= presenceMask; 5335 continue; 5336 } 5337 break; 5338 case 8: // STRING: 5339 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 5340 if ((typeAndOffset & ENFORCE_UTF8_MASK) == 0) { 5341 position = decodeString(data, position, registers); 5342 } else { 5343 position = decodeStringRequireUtf8(data, position, registers); 5344 } 5345 unsafe.putObject(message, fieldOffset, registers.object1); 5346 currentPresenceField |= presenceMask; 5347 continue; 5348 } 5349 break; 5350 case 9: // MESSAGE: 5351 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 5352 final Object current = mutableMessageFieldForMerge(message, pos); 5353 position = 5354 mergeMessageField( 5355 current, getMessageFieldSchema(pos), data, position, limit, registers); 5356 storeMessageField(message, pos, current); 5357 currentPresenceField |= presenceMask; 5358 continue; 5359 } 5360 break; 5361 case 10: // BYTES: 5362 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 5363 position = decodeBytes(data, position, registers); 5364 unsafe.putObject(message, fieldOffset, registers.object1); 5365 currentPresenceField |= presenceMask; 5366 continue; 5367 } 5368 break; 5369 case 12: // ENUM: 5370 if (wireType == WireFormat.WIRETYPE_VARINT) { 5371 position = decodeVarint32(data, position, registers); 5372 unsafe.putInt(message, fieldOffset, registers.int1); 5373 currentPresenceField |= presenceMask; 5374 continue; 5375 } 5376 break; 5377 case 15: // SINT32: 5378 if (wireType == WireFormat.WIRETYPE_VARINT) { 5379 position = decodeVarint32(data, position, registers); 5380 unsafe.putInt( 5381 message, fieldOffset, CodedInputStream.decodeZigZag32(registers.int1)); 5382 currentPresenceField |= presenceMask; 5383 continue; 5384 } 5385 break; 5386 case 16: // SINT64: 5387 if (wireType == WireFormat.WIRETYPE_VARINT) { 5388 position = decodeVarint64(data, position, registers); 5389 unsafe.putLong( 5390 message, fieldOffset, CodedInputStream.decodeZigZag64(registers.long1)); 5391 currentPresenceField |= presenceMask; 5392 continue; 5393 } 5394 break; 5395 default: 5396 break; 5397 } 5398 } else if (fieldType == 27) { 5399 // Handle repeated message field. 5400 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 5401 ProtobufList<?> list = (ProtobufList<?>) unsafe.getObject(message, fieldOffset); 5402 if (!list.isModifiable()) { 5403 final int size = list.size(); 5404 list = 5405 list.mutableCopyWithCapacity( 5406 size == 0 ? AbstractProtobufList.DEFAULT_CAPACITY : size * 2); 5407 unsafe.putObject(message, fieldOffset, list); 5408 } 5409 position = 5410 decodeMessageList( 5411 getMessageFieldSchema(pos), tag, data, position, limit, list, registers); 5412 continue; 5413 } 5414 } else if (fieldType <= 49) { 5415 // Handle all other repeated fields. 5416 final int oldPosition = position; 5417 position = 5418 parseRepeatedField( 5419 message, 5420 data, 5421 position, 5422 limit, 5423 tag, 5424 number, 5425 wireType, 5426 pos, 5427 typeAndOffset, 5428 fieldType, 5429 fieldOffset, 5430 registers); 5431 if (position != oldPosition) { 5432 continue; 5433 } 5434 } else if (fieldType == 50) { 5435 if (wireType == WireFormat.WIRETYPE_LENGTH_DELIMITED) { 5436 final int oldPosition = position; 5437 position = parseMapField(message, data, position, limit, pos, fieldOffset, registers); 5438 if (position != oldPosition) { 5439 continue; 5440 } 5441 } 5442 } else { 5443 final int oldPosition = position; 5444 position = 5445 parseOneofField( 5446 message, 5447 data, 5448 position, 5449 limit, 5450 tag, 5451 number, 5452 wireType, 5453 typeAndOffset, 5454 fieldType, 5455 fieldOffset, 5456 pos, 5457 registers); 5458 if (position != oldPosition) { 5459 continue; 5460 } 5461 } 5462 } 5463 position = decodeUnknownField( 5464 tag, data, position, limit, getMutableUnknownFields(message), registers); 5465 } 5466 if (currentPresenceFieldOffset != NO_PRESENCE_SENTINEL) { 5467 unsafe.putInt(message, (long) currentPresenceFieldOffset, currentPresenceField); 5468 } 5469 if (position != limit) { 5470 throw InvalidProtocolBufferException.parseFailure(); 5471 } 5472 return position; 5473 } 5474 5475 @Override mergeFrom(T message, byte[] data, int position, int limit, Registers registers)5476 public void mergeFrom(T message, byte[] data, int position, int limit, Registers registers) 5477 throws IOException { 5478 if (proto3) { 5479 parseProto3Message(message, data, position, limit, registers); 5480 } else { 5481 parseProto2Message(message, data, position, limit, 0, registers); 5482 } 5483 } 5484 5485 @Override makeImmutable(T message)5486 public void makeImmutable(T message) { 5487 if (!isMutable(message)) { 5488 return; 5489 } 5490 5491 // TODO(b/248560713) decide if we're keeping support for Full in schema classes and handle this 5492 // better. 5493 if (message instanceof GeneratedMessageLite) { 5494 GeneratedMessageLite<?, ?> generatedMessage = ((GeneratedMessageLite<?, ?>) message); 5495 generatedMessage.clearMemoizedSerializedSize(); 5496 generatedMessage.clearMemoizedHashCode(); 5497 generatedMessage.markImmutable(); 5498 } 5499 5500 final int bufferLength = buffer.length; 5501 for (int pos = 0; pos < bufferLength; pos += INTS_PER_FIELD) { 5502 final int typeAndOffset = typeAndOffsetAt(pos); 5503 final long offset = offset(typeAndOffset); 5504 switch (type(typeAndOffset)) { 5505 case 17: // GROUP 5506 case 9: // MESSAGE 5507 if (isFieldPresent(message, pos)) { 5508 getMessageFieldSchema(pos).makeImmutable(UNSAFE.getObject(message, offset)); 5509 } 5510 break; 5511 case 18: // DOUBLE_LIST: 5512 case 19: // FLOAT_LIST: 5513 case 20: // INT64_LIST: 5514 case 21: // UINT64_LIST: 5515 case 22: // INT32_LIST: 5516 case 23: // FIXED64_LIST: 5517 case 24: // FIXED32_LIST: 5518 case 25: // BOOL_LIST: 5519 case 26: // STRING_LIST: 5520 case 27: // MESSAGE_LIST: 5521 case 28: // BYTES_LIST: 5522 case 29: // UINT32_LIST: 5523 case 30: // ENUM_LIST: 5524 case 31: // SFIXED32_LIST: 5525 case 32: // SFIXED64_LIST: 5526 case 33: // SINT32_LIST: 5527 case 34: // SINT64_LIST: 5528 case 35: // DOUBLE_LIST_PACKED: 5529 case 36: // FLOAT_LIST_PACKED: 5530 case 37: // INT64_LIST_PACKED: 5531 case 38: // UINT64_LIST_PACKED: 5532 case 39: // INT32_LIST_PACKED: 5533 case 40: // FIXED64_LIST_PACKED: 5534 case 41: // FIXED32_LIST_PACKED: 5535 case 42: // BOOL_LIST_PACKED: 5536 case 43: // UINT32_LIST_PACKED: 5537 case 44: // ENUM_LIST_PACKED: 5538 case 45: // SFIXED32_LIST_PACKED: 5539 case 46: // SFIXED64_LIST_PACKED: 5540 case 47: // SINT32_LIST_PACKED: 5541 case 48: // SINT64_LIST_PACKED: 5542 case 49: // GROUP_LIST: 5543 listFieldSchema.makeImmutableListAt(message, offset); 5544 break; 5545 case 50: // MAP: 5546 { 5547 Object mapField = UNSAFE.getObject(message, offset); 5548 if (mapField != null) { 5549 UNSAFE.putObject(message, offset, mapFieldSchema.toImmutable(mapField)); 5550 } 5551 } 5552 break; 5553 } 5554 } 5555 unknownFieldSchema.makeImmutable(message); 5556 if (hasExtensions) { 5557 extensionSchema.makeImmutable(message); 5558 } 5559 } 5560 5561 @SuppressWarnings("unchecked") mergeMap( Object message, int pos, Object mapDefaultEntry, ExtensionRegistryLite extensionRegistry, Reader reader)5562 private final <K, V> void mergeMap( 5563 Object message, 5564 int pos, 5565 Object mapDefaultEntry, 5566 ExtensionRegistryLite extensionRegistry, 5567 Reader reader) 5568 throws IOException { 5569 long offset = offset(typeAndOffsetAt(pos)); 5570 Object mapField = UnsafeUtil.getObject(message, offset); 5571 // TODO(xiaofeng): Consider creating separate implementations for full and lite. In lite 5572 // runtime map field will never be null but here we still need to check null because the 5573 // code is shared by both full and lite. It might be better if full/lite uses different 5574 // schema implementations. 5575 if (mapField == null) { 5576 mapField = mapFieldSchema.newMapField(mapDefaultEntry); 5577 UnsafeUtil.putObject(message, offset, mapField); 5578 } else if (mapFieldSchema.isImmutable(mapField)) { 5579 Object oldMapField = mapField; 5580 mapField = mapFieldSchema.newMapField(mapDefaultEntry); 5581 mapFieldSchema.mergeFrom(mapField, oldMapField); 5582 UnsafeUtil.putObject(message, offset, mapField); 5583 } 5584 reader.readMap( 5585 (Map<K, V>) mapFieldSchema.forMutableMapData(mapField), 5586 (Metadata<K, V>) mapFieldSchema.forMapMetadata(mapDefaultEntry), 5587 extensionRegistry); 5588 } 5589 filterMapUnknownEnumValues( Object message, int pos, UB unknownFields, UnknownFieldSchema<UT, UB> unknownFieldSchema, Object containerMessage)5590 private <UT, UB> UB filterMapUnknownEnumValues( 5591 Object message, 5592 int pos, 5593 UB unknownFields, 5594 UnknownFieldSchema<UT, UB> unknownFieldSchema, 5595 Object containerMessage) { 5596 int fieldNumber = numberAt(pos); 5597 long offset = offset(typeAndOffsetAt(pos)); 5598 Object mapField = UnsafeUtil.getObject(message, offset); 5599 if (mapField == null) { 5600 return unknownFields; 5601 } 5602 EnumVerifier enumVerifier = getEnumFieldVerifier(pos); 5603 if (enumVerifier == null) { 5604 return unknownFields; 5605 } 5606 Map<?, ?> mapData = mapFieldSchema.forMutableMapData(mapField); 5607 // Filter unknown enum values. 5608 unknownFields = 5609 filterUnknownEnumMap( 5610 pos, 5611 fieldNumber, 5612 mapData, 5613 enumVerifier, 5614 unknownFields, 5615 unknownFieldSchema, 5616 containerMessage); 5617 return unknownFields; 5618 } 5619 5620 @SuppressWarnings("unchecked") filterUnknownEnumMap( int pos, int number, Map<K, V> mapData, EnumVerifier enumVerifier, UB unknownFields, UnknownFieldSchema<UT, UB> unknownFieldSchema, Object containerMessage)5621 private <K, V, UT, UB> UB filterUnknownEnumMap( 5622 int pos, 5623 int number, 5624 Map<K, V> mapData, 5625 EnumVerifier enumVerifier, 5626 UB unknownFields, 5627 UnknownFieldSchema<UT, UB> unknownFieldSchema, 5628 Object containerMessage) { 5629 Metadata<K, V> metadata = 5630 (Metadata<K, V>) mapFieldSchema.forMapMetadata(getMapFieldDefaultEntry(pos)); 5631 for (Iterator<Map.Entry<K, V>> it = mapData.entrySet().iterator(); it.hasNext(); ) { 5632 Map.Entry<K, V> entry = it.next(); 5633 if (!enumVerifier.isInRange((Integer) entry.getValue())) { 5634 if (unknownFields == null) { 5635 unknownFields = unknownFieldSchema.getBuilderFromMessage(containerMessage); 5636 } 5637 int entrySize = 5638 MapEntryLite.computeSerializedSize(metadata, entry.getKey(), entry.getValue()); 5639 CodedBuilder codedBuilder = ByteString.newCodedBuilder(entrySize); 5640 CodedOutputStream codedOutput = codedBuilder.getCodedOutput(); 5641 try { 5642 MapEntryLite.writeTo(codedOutput, metadata, entry.getKey(), entry.getValue()); 5643 } catch (IOException e) { 5644 // Writing to ByteString CodedOutputStream should not throw IOException. 5645 throw new RuntimeException(e); 5646 } 5647 unknownFieldSchema.addLengthDelimited(unknownFields, number, codedBuilder.build()); 5648 it.remove(); 5649 } 5650 } 5651 return unknownFields; 5652 } 5653 5654 @Override isInitialized(T message)5655 public final boolean isInitialized(T message) { 5656 int currentPresenceFieldOffset = NO_PRESENCE_SENTINEL; 5657 int currentPresenceField = 0; 5658 for (int i = 0; i < checkInitializedCount; i++) { 5659 final int pos = intArray[i]; 5660 final int number = numberAt(pos); 5661 final int typeAndOffset = typeAndOffsetAt(pos); 5662 5663 int presenceMaskAndOffset = buffer[pos + 2]; 5664 final int presenceFieldOffset = presenceMaskAndOffset & OFFSET_MASK; 5665 int presenceMask = 1 << (presenceMaskAndOffset >>> OFFSET_BITS); 5666 if (presenceFieldOffset != currentPresenceFieldOffset) { 5667 currentPresenceFieldOffset = presenceFieldOffset; 5668 if (currentPresenceFieldOffset != NO_PRESENCE_SENTINEL) { 5669 currentPresenceField = UNSAFE.getInt(message, (long) presenceFieldOffset); 5670 } 5671 } 5672 5673 if (isRequired(typeAndOffset)) { 5674 if (!isFieldPresent( 5675 message, pos, currentPresenceFieldOffset, currentPresenceField, presenceMask)) { 5676 return false; 5677 } 5678 // If a required message field is set but has no required fields of it's own, we still 5679 // proceed and check the message is initialized. It should be fairly cheap to check these 5680 // messages but is worth documenting. 5681 } 5682 // Check nested message and groups. 5683 switch (type(typeAndOffset)) { 5684 case 9: // MESSAGE 5685 case 17: // GROUP 5686 if (isFieldPresent( 5687 message, pos, currentPresenceFieldOffset, currentPresenceField, presenceMask) 5688 && !isInitialized(message, typeAndOffset, getMessageFieldSchema(pos))) { 5689 return false; 5690 } 5691 break; 5692 case 27: // MESSAGE_LIST 5693 case 49: // GROUP_LIST 5694 if (!isListInitialized(message, typeAndOffset, pos)) { 5695 return false; 5696 } 5697 break; 5698 case 60: // ONEOF_MESSAGE 5699 case 68: // ONEOF_GROUP 5700 if (isOneofPresent(message, number, pos) 5701 && !isInitialized(message, typeAndOffset, getMessageFieldSchema(pos))) { 5702 return false; 5703 } 5704 break; 5705 case 50: // MAP 5706 if (!isMapInitialized(message, typeAndOffset, pos)) { 5707 return false; 5708 } 5709 break; 5710 default: 5711 break; 5712 } 5713 } 5714 5715 if (hasExtensions) { 5716 if (!extensionSchema.getExtensions(message).isInitialized()) { 5717 return false; 5718 } 5719 } 5720 5721 return true; 5722 } 5723 isInitialized(Object message, int typeAndOffset, Schema schema)5724 private static boolean isInitialized(Object message, int typeAndOffset, Schema schema) { 5725 Object nested = UnsafeUtil.getObject(message, offset(typeAndOffset)); 5726 return schema.isInitialized(nested); 5727 } 5728 isListInitialized(Object message, int typeAndOffset, int pos)5729 private <N> boolean isListInitialized(Object message, int typeAndOffset, int pos) { 5730 @SuppressWarnings("unchecked") 5731 List<N> list = (List<N>) UnsafeUtil.getObject(message, offset(typeAndOffset)); 5732 if (list.isEmpty()) { 5733 return true; 5734 } 5735 5736 Schema schema = getMessageFieldSchema(pos); 5737 for (int i = 0; i < list.size(); i++) { 5738 N nested = list.get(i); 5739 if (!schema.isInitialized(nested)) { 5740 return false; 5741 } 5742 } 5743 return true; 5744 } 5745 isMapInitialized(T message, int typeAndOffset, int pos)5746 private boolean isMapInitialized(T message, int typeAndOffset, int pos) { 5747 Map<?, ?> map = mapFieldSchema.forMapData(UnsafeUtil.getObject(message, offset(typeAndOffset))); 5748 if (map.isEmpty()) { 5749 return true; 5750 } 5751 Object mapDefaultEntry = getMapFieldDefaultEntry(pos); 5752 MapEntryLite.Metadata<?, ?> metadata = mapFieldSchema.forMapMetadata(mapDefaultEntry); 5753 if (metadata.valueType.getJavaType() != WireFormat.JavaType.MESSAGE) { 5754 return true; 5755 } 5756 // TODO(dweis): Use schema cache. 5757 Schema schema = null; 5758 for (Object nested : map.values()) { 5759 if (schema == null) { 5760 schema = Protobuf.getInstance().schemaFor(nested.getClass()); 5761 } 5762 if (!schema.isInitialized(nested)) { 5763 return false; 5764 } 5765 } 5766 return true; 5767 } 5768 writeString(int fieldNumber, Object value, Writer writer)5769 private void writeString(int fieldNumber, Object value, Writer writer) throws IOException { 5770 if (value instanceof String) { 5771 writer.writeString(fieldNumber, (String) value); 5772 } else { 5773 writer.writeBytes(fieldNumber, (ByteString) value); 5774 } 5775 } 5776 readString(Object message, int typeAndOffset, Reader reader)5777 private void readString(Object message, int typeAndOffset, Reader reader) throws IOException { 5778 if (isEnforceUtf8(typeAndOffset)) { 5779 // Enforce valid UTF-8 on the read. 5780 UnsafeUtil.putObject(message, offset(typeAndOffset), reader.readStringRequireUtf8()); 5781 } else if (lite) { 5782 // Lite messages use String fields to store strings. Read a string but do not 5783 // enforce UTF-8 5784 UnsafeUtil.putObject(message, offset(typeAndOffset), reader.readString()); 5785 } else { 5786 // Full runtime messages use Objects to store either a String or ByteString. Read 5787 // the string as a ByteString and do not enforce UTF-8. 5788 UnsafeUtil.putObject(message, offset(typeAndOffset), reader.readBytes()); 5789 } 5790 } 5791 readStringList(Object message, int typeAndOffset, Reader reader)5792 private void readStringList(Object message, int typeAndOffset, Reader reader) throws IOException { 5793 if (isEnforceUtf8(typeAndOffset)) { 5794 reader.readStringListRequireUtf8( 5795 listFieldSchema.<String>mutableListAt(message, offset(typeAndOffset))); 5796 } else { 5797 reader.readStringList(listFieldSchema.<String>mutableListAt(message, offset(typeAndOffset))); 5798 } 5799 } 5800 readMessageList( Object message, int typeAndOffset, Reader reader, Schema<E> schema, ExtensionRegistryLite extensionRegistry)5801 private <E> void readMessageList( 5802 Object message, 5803 int typeAndOffset, 5804 Reader reader, 5805 Schema<E> schema, 5806 ExtensionRegistryLite extensionRegistry) 5807 throws IOException { 5808 long offset = offset(typeAndOffset); 5809 reader.readMessageList( 5810 listFieldSchema.<E>mutableListAt(message, offset), schema, extensionRegistry); 5811 } 5812 readGroupList( Object message, long offset, Reader reader, Schema<E> schema, ExtensionRegistryLite extensionRegistry)5813 private <E> void readGroupList( 5814 Object message, 5815 long offset, 5816 Reader reader, 5817 Schema<E> schema, 5818 ExtensionRegistryLite extensionRegistry) 5819 throws IOException { 5820 reader.readGroupList( 5821 listFieldSchema.<E>mutableListAt(message, offset), schema, extensionRegistry); 5822 } 5823 numberAt(int pos)5824 private int numberAt(int pos) { 5825 return buffer[pos]; 5826 } 5827 typeAndOffsetAt(int pos)5828 private int typeAndOffsetAt(int pos) { 5829 return buffer[pos + 1]; 5830 } 5831 presenceMaskAndOffsetAt(int pos)5832 private int presenceMaskAndOffsetAt(int pos) { 5833 return buffer[pos + 2]; 5834 } 5835 type(int value)5836 private static int type(int value) { 5837 return (value & FIELD_TYPE_MASK) >>> OFFSET_BITS; 5838 } 5839 isRequired(int value)5840 private static boolean isRequired(int value) { 5841 return (value & REQUIRED_MASK) != 0; 5842 } 5843 isEnforceUtf8(int value)5844 private static boolean isEnforceUtf8(int value) { 5845 return (value & ENFORCE_UTF8_MASK) != 0; 5846 } 5847 offset(int value)5848 private static long offset(int value) { 5849 return value & OFFSET_MASK; 5850 } 5851 isMutable(Object message)5852 private static boolean isMutable(Object message) { 5853 if (message == null) { 5854 return false; 5855 } 5856 5857 // TODO(b/248560713) decide if we're keeping support for Full in schema classes and handle this 5858 // better. 5859 if (message instanceof GeneratedMessageLite<?, ?>) { 5860 return ((GeneratedMessageLite<?, ?>) message).isMutable(); 5861 } 5862 5863 // For other types, we'll assume this is true because that's what was 5864 // happening before we started checking. 5865 return true; 5866 } 5867 checkMutable(Object message)5868 private static void checkMutable(Object message) { 5869 if (!isMutable(message)) { 5870 throw new IllegalArgumentException("Mutating immutable message: " + message); 5871 } 5872 } 5873 doubleAt(T message, long offset)5874 private static <T> double doubleAt(T message, long offset) { 5875 return UnsafeUtil.getDouble(message, offset); 5876 } 5877 floatAt(T message, long offset)5878 private static <T> float floatAt(T message, long offset) { 5879 return UnsafeUtil.getFloat(message, offset); 5880 } 5881 intAt(T message, long offset)5882 private static <T> int intAt(T message, long offset) { 5883 return UnsafeUtil.getInt(message, offset); 5884 } 5885 longAt(T message, long offset)5886 private static <T> long longAt(T message, long offset) { 5887 return UnsafeUtil.getLong(message, offset); 5888 } 5889 booleanAt(T message, long offset)5890 private static <T> boolean booleanAt(T message, long offset) { 5891 return UnsafeUtil.getBoolean(message, offset); 5892 } 5893 oneofDoubleAt(T message, long offset)5894 private static <T> double oneofDoubleAt(T message, long offset) { 5895 return ((Double) UnsafeUtil.getObject(message, offset)).doubleValue(); 5896 } 5897 oneofFloatAt(T message, long offset)5898 private static <T> float oneofFloatAt(T message, long offset) { 5899 return ((Float) UnsafeUtil.getObject(message, offset)).floatValue(); 5900 } 5901 oneofIntAt(T message, long offset)5902 private static <T> int oneofIntAt(T message, long offset) { 5903 return ((Integer) UnsafeUtil.getObject(message, offset)).intValue(); 5904 } 5905 oneofLongAt(T message, long offset)5906 private static <T> long oneofLongAt(T message, long offset) { 5907 return ((Long) UnsafeUtil.getObject(message, offset)).longValue(); 5908 } 5909 oneofBooleanAt(T message, long offset)5910 private static <T> boolean oneofBooleanAt(T message, long offset) { 5911 return ((Boolean) UnsafeUtil.getObject(message, offset)).booleanValue(); 5912 } 5913 5914 /** Returns true the field is present in both messages, or neither. */ arePresentForEquals(T message, T other, int pos)5915 private boolean arePresentForEquals(T message, T other, int pos) { 5916 return isFieldPresent(message, pos) == isFieldPresent(other, pos); 5917 } 5918 isFieldPresent( T message, int pos, int presenceFieldOffset, int presenceField, int presenceMask)5919 private boolean isFieldPresent( 5920 T message, int pos, int presenceFieldOffset, int presenceField, int presenceMask) { 5921 if (presenceFieldOffset == NO_PRESENCE_SENTINEL) { 5922 return isFieldPresent(message, pos); 5923 } else { 5924 return (presenceField & presenceMask) != 0; 5925 } 5926 } 5927 isFieldPresent(T message, int pos)5928 private boolean isFieldPresent(T message, int pos) { 5929 final int presenceMaskAndOffset = presenceMaskAndOffsetAt(pos); 5930 final long presenceFieldOffset = presenceMaskAndOffset & OFFSET_MASK; 5931 if (presenceFieldOffset == NO_PRESENCE_SENTINEL) { 5932 final int typeAndOffset = typeAndOffsetAt(pos); 5933 final long offset = offset(typeAndOffset); 5934 switch (type(typeAndOffset)) { 5935 case 0: // DOUBLE: 5936 return UnsafeUtil.getDouble(message, offset) != 0D; 5937 case 1: // FLOAT: 5938 return UnsafeUtil.getFloat(message, offset) != 0F; 5939 case 2: // INT64: 5940 return UnsafeUtil.getLong(message, offset) != 0L; 5941 case 3: // UINT64: 5942 return UnsafeUtil.getLong(message, offset) != 0L; 5943 case 4: // INT32: 5944 return UnsafeUtil.getInt(message, offset) != 0; 5945 case 5: // FIXED64: 5946 return UnsafeUtil.getLong(message, offset) != 0L; 5947 case 6: // FIXED32: 5948 return UnsafeUtil.getInt(message, offset) != 0; 5949 case 7: // BOOL: 5950 return UnsafeUtil.getBoolean(message, offset); 5951 case 8: // STRING: 5952 Object value = UnsafeUtil.getObject(message, offset); 5953 if (value instanceof String) { 5954 return !((String) value).isEmpty(); 5955 } else if (value instanceof ByteString) { 5956 return !ByteString.EMPTY.equals(value); 5957 } else { 5958 throw new IllegalArgumentException(); 5959 } 5960 case 9: // MESSAGE: 5961 return UnsafeUtil.getObject(message, offset) != null; 5962 case 10: // BYTES: 5963 return !ByteString.EMPTY.equals(UnsafeUtil.getObject(message, offset)); 5964 case 11: // UINT32: 5965 return UnsafeUtil.getInt(message, offset) != 0; 5966 case 12: // ENUM: 5967 return UnsafeUtil.getInt(message, offset) != 0; 5968 case 13: // SFIXED32: 5969 return UnsafeUtil.getInt(message, offset) != 0; 5970 case 14: // SFIXED64: 5971 return UnsafeUtil.getLong(message, offset) != 0L; 5972 case 15: // SINT32: 5973 return UnsafeUtil.getInt(message, offset) != 0; 5974 case 16: // SINT64: 5975 return UnsafeUtil.getLong(message, offset) != 0L; 5976 case 17: // GROUP: 5977 return UnsafeUtil.getObject(message, offset) != null; 5978 default: 5979 throw new IllegalArgumentException(); 5980 } 5981 } else { 5982 final int presenceMask = 1 << (presenceMaskAndOffset >>> OFFSET_BITS); 5983 return (UnsafeUtil.getInt(message, presenceMaskAndOffset & OFFSET_MASK) & presenceMask) != 0; 5984 } 5985 } 5986 setFieldPresent(T message, int pos)5987 private void setFieldPresent(T message, int pos) { 5988 int presenceMaskAndOffset = presenceMaskAndOffsetAt(pos); 5989 final long presenceFieldOffset = presenceMaskAndOffset & OFFSET_MASK; 5990 if (presenceFieldOffset == NO_PRESENCE_SENTINEL) { 5991 return; 5992 } 5993 final int presenceMask = 1 << (presenceMaskAndOffset >>> OFFSET_BITS); 5994 UnsafeUtil.putInt( 5995 message, 5996 presenceFieldOffset, 5997 UnsafeUtil.getInt(message, presenceFieldOffset) | presenceMask); 5998 } 5999 isOneofPresent(T message, int fieldNumber, int pos)6000 private boolean isOneofPresent(T message, int fieldNumber, int pos) { 6001 int presenceMaskAndOffset = presenceMaskAndOffsetAt(pos); 6002 return UnsafeUtil.getInt(message, presenceMaskAndOffset & OFFSET_MASK) == fieldNumber; 6003 } 6004 isOneofCaseEqual(T message, T other, int pos)6005 private boolean isOneofCaseEqual(T message, T other, int pos) { 6006 int presenceMaskAndOffset = presenceMaskAndOffsetAt(pos); 6007 return UnsafeUtil.getInt(message, presenceMaskAndOffset & OFFSET_MASK) 6008 == UnsafeUtil.getInt(other, presenceMaskAndOffset & OFFSET_MASK); 6009 } 6010 setOneofPresent(T message, int fieldNumber, int pos)6011 private void setOneofPresent(T message, int fieldNumber, int pos) { 6012 int presenceMaskAndOffset = presenceMaskAndOffsetAt(pos); 6013 UnsafeUtil.putInt(message, presenceMaskAndOffset & OFFSET_MASK, fieldNumber); 6014 } 6015 positionForFieldNumber(final int number)6016 private int positionForFieldNumber(final int number) { 6017 if (number >= minFieldNumber && number <= maxFieldNumber) { 6018 return slowPositionForFieldNumber(number, 0); 6019 } 6020 return -1; 6021 } 6022 positionForFieldNumber(final int number, final int min)6023 private int positionForFieldNumber(final int number, final int min) { 6024 if (number >= minFieldNumber && number <= maxFieldNumber) { 6025 return slowPositionForFieldNumber(number, min); 6026 } 6027 return -1; 6028 } 6029 slowPositionForFieldNumber(final int number, int min)6030 private int slowPositionForFieldNumber(final int number, int min) { 6031 int max = buffer.length / INTS_PER_FIELD - 1; 6032 while (min <= max) { 6033 // Find the midpoint address. 6034 final int mid = (max + min) >>> 1; 6035 final int pos = mid * INTS_PER_FIELD; 6036 final int midFieldNumber = numberAt(pos); 6037 if (number == midFieldNumber) { 6038 // Found the field. 6039 return pos; 6040 } 6041 if (number < midFieldNumber) { 6042 // Search the lower half. 6043 max = mid - 1; 6044 } else { 6045 // Search the upper half. 6046 min = mid + 1; 6047 } 6048 } 6049 return -1; 6050 } 6051 getSchemaSize()6052 int getSchemaSize() { 6053 return buffer.length * 3; 6054 } 6055 } 6056