bool MergePartialFromCodedStreamInlined()

in cdk/extra/protobuf/protobuf-3.19.6/src/google/protobuf/generated_message_table_driven_lite.h [367:848]


bool MergePartialFromCodedStreamInlined(MessageLite* msg,
                                        const ParseTable& table,
                                        io::CodedInputStream* input) {
  // We require that has_bits are present, as to avoid having to check for them
  // for every field.
  //
  // TODO(ckennelly):  Make this a compile-time parameter with templates.
  GOOGLE_DCHECK_GE(table.has_bits_offset, 0);
  uint32_t* has_bits = Raw<uint32_t>(msg, table.has_bits_offset);
  GOOGLE_DCHECK(has_bits != nullptr);

  while (true) {
    uint32_t tag = input->ReadTagWithCutoffNoLastTag(kMaxTag).first;
    const WireFormatLite::WireType wire_type =
        WireFormatLite::GetTagWireType(tag);
    const int field_number = WireFormatLite::GetTagFieldNumber(tag);

    if (PROTOBUF_PREDICT_FALSE(field_number > table.max_field_number)) {
      // check for possible extensions
      if (UnknownFieldHandler::ParseExtension(msg, table, input, tag)) {
        // successfully parsed
        continue;
      }

      if (PROTOBUF_PREDICT_FALSE(
              !UnknownFieldHandler::Skip(msg, table, input, tag))) {
        return false;
      }

      continue;
    }

    // We implicitly verify that data points to a valid field as we check the
    // wire types.  Entries in table.fields[i] that do not correspond to valid
    // field numbers have their normal_wiretype and packed_wiretype fields set
    // with the kInvalidMask value.  As wire_type cannot take on that value, we
    // will never match.
    const ParseTableField* data = table.fields + field_number;

    // TODO(ckennelly): Avoid sign extension
    const int64_t presence_index = data->presence_index;
    const int64_t offset = data->offset;
    const unsigned char processing_type = data->processing_type;

    if (data->normal_wiretype == static_cast<unsigned char>(wire_type)) {
      switch (processing_type) {
#define HANDLE_TYPE(TYPE, CPPTYPE)                                             \
  case (WireFormatLite::TYPE_##TYPE): {                                        \
    CPPTYPE value;                                                             \
    if (PROTOBUF_PREDICT_FALSE(                                                \
            (!WireFormatLite::ReadPrimitive<                                   \
                CPPTYPE, WireFormatLite::TYPE_##TYPE>(input, &value)))) {      \
      return false;                                                            \
    }                                                                          \
    SetField(msg, has_bits, presence_index, offset, value);                    \
    break;                                                                     \
  }                                                                            \
  case (WireFormatLite::TYPE_##TYPE) | kRepeatedMask: {                        \
    RepeatedField<CPPTYPE>* values = Raw<RepeatedField<CPPTYPE>>(msg, offset); \
    if (PROTOBUF_PREDICT_FALSE((!WireFormatLite::ReadRepeatedPrimitive<        \
                                CPPTYPE, WireFormatLite::TYPE_##TYPE>(         \
            data->tag_size, tag, input, values)))) {                           \
      return false;                                                            \
    }                                                                          \
    break;                                                                     \
  }                                                                            \
  case (WireFormatLite::TYPE_##TYPE) | kOneofMask: {                           \
    uint32_t* oneof_case = Raw<uint32_t>(msg, table.oneof_case_offset);        \
    CPPTYPE value;                                                             \
    if (PROTOBUF_PREDICT_FALSE(                                                \
            (!WireFormatLite::ReadPrimitive<                                   \
                CPPTYPE, WireFormatLite::TYPE_##TYPE>(input, &value)))) {      \
      return false;                                                            \
    }                                                                          \
    ClearOneofField(table.fields[oneof_case[presence_index]], msg->GetArena(), \
                    msg);                                                      \
    SetOneofField(msg, oneof_case, presence_index, offset, field_number,       \
                  value);                                                      \
    break;                                                                     \
  }

        HANDLE_TYPE(INT32, int32_t)
        HANDLE_TYPE(INT64, int64_t)
        HANDLE_TYPE(SINT32, int32_t)
        HANDLE_TYPE(SINT64, int64_t)
        HANDLE_TYPE(UINT32, uint32_t)
        HANDLE_TYPE(UINT64, uint64_t)

        HANDLE_TYPE(FIXED32, uint32_t)
        HANDLE_TYPE(FIXED64, uint64_t)
        HANDLE_TYPE(SFIXED32, int32_t)
        HANDLE_TYPE(SFIXED64, int64_t)

        HANDLE_TYPE(FLOAT, float)
        HANDLE_TYPE(DOUBLE, double)

        HANDLE_TYPE(BOOL, bool)
#undef HANDLE_TYPE
        case WireFormatLite::TYPE_BYTES:
#ifndef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        case WireFormatLite::TYPE_STRING:
#endif  // GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        {
          Arena* const arena = msg->GetArena();
          const void* default_ptr = table.aux[field_number].strings.default_ptr;

          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleString<UnknownFieldHandler, Cardinality_SINGULAR,
                                 false, StringType_STRING>(
                      input, msg, arena, has_bits, presence_index, offset,
                      default_ptr, nullptr)))) {
            return false;
          }
          break;
        }
        case TYPE_BYTES_INLINED:
#ifndef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        case TYPE_STRING_INLINED:
#endif  // !GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        {
          Arena* const arena = msg->GetArena();
          const void* default_ptr = table.aux[field_number].strings.default_ptr;

          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleString<UnknownFieldHandler, Cardinality_SINGULAR,
                                 false, StringType_INLINED>(
                      input, msg, arena, has_bits, presence_index, offset,
                      default_ptr, nullptr)))) {
            return false;
          }
          break;
        }
        case WireFormatLite::TYPE_BYTES | kOneofMask:
#ifndef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        case WireFormatLite::TYPE_STRING | kOneofMask:
#endif  // !GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        {
          Arena* const arena = msg->GetArena();
          uint32_t* oneof_case = Raw<uint32_t>(msg, table.oneof_case_offset);
          const void* default_ptr = table.aux[field_number].strings.default_ptr;

          ResetOneofField<ProcessingType_STRING>(
              table, field_number, arena, msg, oneof_case + presence_index,
              offset, default_ptr);

          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleString<UnknownFieldHandler, Cardinality_ONEOF, false,
                                 StringType_STRING>(input, msg, arena, has_bits,
                                                    presence_index, offset,
                                                    default_ptr, nullptr)))) {
            return false;
          }
          break;
        }
        case (WireFormatLite::TYPE_BYTES) | kRepeatedMask:
        case TYPE_BYTES_INLINED | kRepeatedMask:
#ifndef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        case (WireFormatLite::TYPE_STRING) | kRepeatedMask:
        case TYPE_STRING_INLINED | kRepeatedMask:
#endif  // !GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        {
          Arena* const arena = msg->GetArena();
          const void* default_ptr = table.aux[field_number].strings.default_ptr;

          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleString<UnknownFieldHandler, Cardinality_REPEATED,
                                 false, StringType_STRING>(
                      input, msg, arena, has_bits, presence_index, offset,
                      default_ptr, nullptr)))) {
            return false;
          }
          break;
        }
#ifdef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        case (WireFormatLite::TYPE_STRING): {
          Arena* const arena = msg->GetArena();
          const void* default_ptr = table.aux[field_number].strings.default_ptr;
          const char* field_name = table.aux[field_number].strings.field_name;

          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleString<UnknownFieldHandler, Cardinality_SINGULAR,
                                 true, StringType_STRING>(
                      input, msg, arena, has_bits, presence_index, offset,
                      default_ptr, field_name)))) {
            return false;
          }
          break;
        }
        case TYPE_STRING_INLINED | kRepeatedMask:
        case (WireFormatLite::TYPE_STRING) | kRepeatedMask: {
          Arena* const arena = msg->GetArena();
          const void* default_ptr = table.aux[field_number].strings.default_ptr;
          const char* field_name = table.aux[field_number].strings.field_name;

          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleString<UnknownFieldHandler, Cardinality_REPEATED,
                                 true, StringType_STRING>(
                      input, msg, arena, has_bits, presence_index, offset,
                      default_ptr, field_name)))) {
            return false;
          }
          break;
        }
        case (WireFormatLite::TYPE_STRING) | kOneofMask: {
          Arena* const arena = msg->GetArena();
          uint32_t* oneof_case = Raw<uint32_t>(msg, table.oneof_case_offset);
          const void* default_ptr = table.aux[field_number].strings.default_ptr;
          const char* field_name = table.aux[field_number].strings.field_name;

          ResetOneofField<ProcessingType_STRING>(
              table, field_number, arena, msg, oneof_case + presence_index,
              offset, default_ptr);

          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleString<UnknownFieldHandler, Cardinality_ONEOF, true,
                                 StringType_STRING>(
                      input, msg, arena, has_bits, presence_index, offset,
                      default_ptr, field_name)))) {
            return false;
          }
          break;
        }
#endif  // GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        case WireFormatLite::TYPE_ENUM: {
          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleEnum<UnknownFieldHandler, Cardinality_SINGULAR>(
                      table, input, msg, has_bits, presence_index, offset, tag,
                      field_number)))) {
            return false;
          }
          break;
        }
        case WireFormatLite::TYPE_ENUM | kRepeatedMask: {
          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleEnum<UnknownFieldHandler, Cardinality_REPEATED>(
                      table, input, msg, has_bits, presence_index, offset, tag,
                      field_number)))) {
            return false;
          }
          break;
        }
        case WireFormatLite::TYPE_ENUM | kOneofMask: {
          uint32_t* oneof_case = Raw<uint32_t>(msg, table.oneof_case_offset);
          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleEnum<UnknownFieldHandler, Cardinality_ONEOF>(
                      table, input, msg, oneof_case, presence_index, offset,
                      tag, field_number)))) {
            return false;
          }
          break;
        }
        case WireFormatLite::TYPE_GROUP: {
          MessageLite** submsg_holder =
              MutableField<MessageLite*>(msg, has_bits, presence_index, offset);
          MessageLite* submsg = *submsg_holder;

          if (submsg == nullptr) {
            Arena* const arena = msg->GetArena();
            const MessageLite* prototype =
                table.aux[field_number].messages.default_message();
            submsg = prototype->New(arena);
            *submsg_holder = submsg;
          }

          if (PROTOBUF_PREDICT_FALSE(
                  !WireFormatLite::ReadGroup(field_number, input, submsg))) {
            return false;
          }

          break;
        }
        case WireFormatLite::TYPE_GROUP | kRepeatedMask: {
          RepeatedPtrFieldBase* field = Raw<RepeatedPtrFieldBase>(msg, offset);
          const MessageLite* prototype =
              table.aux[field_number].messages.default_message();
          GOOGLE_DCHECK(prototype != nullptr);

          MessageLite* submsg =
              MergePartialFromCodedStreamHelper::Add(field, prototype);

          if (PROTOBUF_PREDICT_FALSE(
                  !WireFormatLite::ReadGroup(field_number, input, submsg))) {
            return false;
          }

          break;
        }
        case WireFormatLite::TYPE_MESSAGE: {
          MessageLite** submsg_holder =
              MutableField<MessageLite*>(msg, has_bits, presence_index, offset);
          MessageLite* submsg = *submsg_holder;

          if (submsg == nullptr) {
            Arena* const arena = msg->GetArena();
            const MessageLite* prototype =
                table.aux[field_number].messages.default_message();
            if (prototype == nullptr) {
              prototype = ImplicitWeakMessage::default_instance();
            }
            submsg = prototype->New(arena);
            *submsg_holder = submsg;
          }

          if (PROTOBUF_PREDICT_FALSE(
                  !WireFormatLite::ReadMessage(input, submsg))) {
            return false;
          }

          break;
        }
        // TODO(ckennelly):  Adapt ReadMessageNoVirtualNoRecursionDepth and
        // manage input->IncrementRecursionDepth() here.
        case WireFormatLite::TYPE_MESSAGE | kRepeatedMask: {
          RepeatedPtrFieldBase* field = Raw<RepeatedPtrFieldBase>(msg, offset);
          const MessageLite* prototype =
              table.aux[field_number].messages.default_message();
          if (prototype == nullptr) {
            prototype = ImplicitWeakMessage::default_instance();
          }

          MessageLite* submsg =
              MergePartialFromCodedStreamHelper::Add(field, prototype);

          if (PROTOBUF_PREDICT_FALSE(
                  !WireFormatLite::ReadMessage(input, submsg))) {
            return false;
          }

          break;
        }
        case WireFormatLite::TYPE_MESSAGE | kOneofMask: {
          Arena* const arena = msg->GetArena();
          uint32_t* oneof_case = Raw<uint32_t>(msg, table.oneof_case_offset);
          MessageLite** submsg_holder = Raw<MessageLite*>(msg, offset);
          ResetOneofField<ProcessingType_MESSAGE>(
              table, field_number, arena, msg, oneof_case + presence_index,
              offset, nullptr);
          MessageLite* submsg = *submsg_holder;

          if (PROTOBUF_PREDICT_FALSE(
                  !WireFormatLite::ReadMessage(input, submsg))) {
            return false;
          }

          break;
        }
#ifdef GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        case TYPE_STRING_INLINED: {
          Arena* const arena = msg->GetArena();
          const void* default_ptr = table.aux[field_number].strings.default_ptr;
          const char* field_name = table.aux[field_number].strings.field_name;

          if (PROTOBUF_PREDICT_FALSE(
                  (!HandleString<UnknownFieldHandler, Cardinality_SINGULAR,
                                 true, StringType_INLINED>(
                      input, msg, arena, has_bits, presence_index, offset,
                      default_ptr, field_name)))) {
            return false;
          }
          break;
        }
#endif  // GOOGLE_PROTOBUF_UTF8_VALIDATION_ENABLED
        case TYPE_MAP: {
          if (PROTOBUF_PREDICT_FALSE(!(*table.aux[field_number].maps.parse_map)(
                  input, Raw<void>(msg, offset)))) {
            return false;
          }
          break;
        }
        case 0: {
          // Done.
          input->SetLastTag(tag);
          return true;
        }
        default:
          PROTOBUF_ASSUME(false);
      }
    } else if (data->packed_wiretype == static_cast<unsigned char>(wire_type)) {
      // Non-packable fields have their packed_wiretype masked with
      // kNotPackedMask, which is impossible to match here.
      GOOGLE_DCHECK(processing_type & kRepeatedMask);
      GOOGLE_DCHECK_NE(processing_type, kRepeatedMask);
      GOOGLE_DCHECK_EQ(0, processing_type & kOneofMask);

      GOOGLE_DCHECK_NE(TYPE_BYTES_INLINED | kRepeatedMask, processing_type);
      GOOGLE_DCHECK_NE(TYPE_STRING_INLINED | kRepeatedMask, processing_type);

      // Mask out kRepeatedMask bit, allowing the jump table to be smaller.
      switch (static_cast<WireFormatLite::FieldType>(processing_type ^
                                                     kRepeatedMask)) {
#define HANDLE_PACKED_TYPE(TYPE, CPPTYPE, CPPTYPE_METHOD)                      \
  case WireFormatLite::TYPE_##TYPE: {                                          \
    RepeatedField<CPPTYPE>* values = Raw<RepeatedField<CPPTYPE>>(msg, offset); \
    if (PROTOBUF_PREDICT_FALSE(                                                \
            (!WireFormatLite::ReadPackedPrimitive<                             \
                CPPTYPE, WireFormatLite::TYPE_##TYPE>(input, values)))) {      \
      return false;                                                            \
    }                                                                          \
    break;                                                                     \
  }

        HANDLE_PACKED_TYPE(INT32, int32_t, Int32)
        HANDLE_PACKED_TYPE(INT64, int64_t, Int64)
        HANDLE_PACKED_TYPE(SINT32, int32_t, Int32)
        HANDLE_PACKED_TYPE(SINT64, int64_t, Int64)
        HANDLE_PACKED_TYPE(UINT32, uint32_t, UInt32)
        HANDLE_PACKED_TYPE(UINT64, uint64_t, UInt64)

        HANDLE_PACKED_TYPE(FIXED32, uint32_t, UInt32)
        HANDLE_PACKED_TYPE(FIXED64, uint64_t, UInt64)
        HANDLE_PACKED_TYPE(SFIXED32, int32_t, Int32)
        HANDLE_PACKED_TYPE(SFIXED64, int64_t, Int64)

        HANDLE_PACKED_TYPE(FLOAT, float, Float)
        HANDLE_PACKED_TYPE(DOUBLE, double, Double)

        HANDLE_PACKED_TYPE(BOOL, bool, Bool)
#undef HANDLE_PACKED_TYPE
        case WireFormatLite::TYPE_ENUM: {
          // To avoid unnecessarily calling MutableUnknownFields (which mutates
          // InternalMetadata) when all inputs in the repeated series
          // are valid, we implement our own parser rather than call
          // WireFormat::ReadPackedEnumPreserveUnknowns.
          uint32_t length;
          if (PROTOBUF_PREDICT_FALSE(!input->ReadVarint32(&length))) {
            return false;
          }

          AuxiliaryParseTableField::EnumValidator validator =
              table.aux[field_number].enums.validator;
          RepeatedField<int>* values = Raw<RepeatedField<int>>(msg, offset);

          io::CodedInputStream::Limit limit = input->PushLimit(length);
          while (input->BytesUntilLimit() > 0) {
            int value;
            if (PROTOBUF_PREDICT_FALSE(
                    (!WireFormatLite::ReadPrimitive<
                        int, WireFormatLite::TYPE_ENUM>(input, &value)))) {
              return false;
            }

            if (validator == nullptr || validator(value)) {
              values->Add(value);
            } else {
              // TODO(ckennelly): Consider caching here.
              UnknownFieldHandler::Varint(msg, table, tag, value);
            }
          }
          input->PopLimit(limit);

          break;
        }
        case WireFormatLite::TYPE_STRING:
        case WireFormatLite::TYPE_GROUP:
        case WireFormatLite::TYPE_MESSAGE:
        case WireFormatLite::TYPE_BYTES:
          GOOGLE_DCHECK(false);
          return false;
        default:
          PROTOBUF_ASSUME(false);
      }
    } else {
      if (wire_type == WireFormatLite::WIRETYPE_END_GROUP) {
        // Must be the end of the message.
        input->SetLastTag(tag);
        return true;
      }

      // check for possible extensions
      if (UnknownFieldHandler::ParseExtension(msg, table, input, tag)) {
        // successfully parsed
        continue;
      }

      // process unknown field.
      if (PROTOBUF_PREDICT_FALSE(
              !UnknownFieldHandler::Skip(msg, table, input, tag))) {
        return false;
      }
    }
  }
}  // NOLINT(readability/fn_size)