// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc.  All rights reserved.
// https://developers.google.com/protocol-buffers/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
//     * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//     * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//     * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

// Author: kenton@google.com (Kenton Varda)
//  Based on original Protocol Buffers design by
//  Sanjay Ghemawat, Jeff Dean, and others.
//
// This file contains the CodedInputStream and CodedOutputStream classes,
// which wrap a ZeroCopyInputStream or ZeroCopyOutputStream, respectively,
// and allow you to read or write individual pieces of data in various
// formats.  In particular, these implement the varint encoding for
// integers, a simple variable-length encoding in which smaller numbers
// take fewer bytes.
//
// Typically these classes will only be used internally by the protocol
// buffer library in order to encode and decode protocol buffers.  Clients
// of the library only need to know about this class if they wish to write
// custom message parsing or serialization procedures.
//
// CodedOutputStream example:
//   // Write some data to "myfile".  First we write a 4-byte "magic number"
//   // to identify the file type, then write a length-delimited string.  The
//   // string is composed of a varint giving the length followed by the raw
//   // bytes.
//   int fd = open("myfile", O_CREAT | O_WRONLY);
//   ZeroCopyOutputStream* raw_output = new FileOutputStream(fd);
//   CodedOutputStream* coded_output = new CodedOutputStream(raw_output);
//
//   int magic_number = 1234;
//   char text[] = "Hello world!";
//   coded_output->WriteLittleEndian32(magic_number);
//   coded_output->WriteVarint32(strlen(text));
//   coded_output->WriteRaw(text, strlen(text));
//
//   delete coded_output;
//   delete raw_output;
//   close(fd);
//
// CodedInputStream example:
//   // Read a file created by the above code.
//   int fd = open("myfile", O_RDONLY);
//   ZeroCopyInputStream* raw_input = new FileInputStream(fd);
//   CodedInputStream* coded_input = new CodedInputStream(raw_input);
//
//   coded_input->ReadLittleEndian32(&magic_number);
//   if (magic_number != 1234) {
//     cerr << "File not in expected format." << endl;
//     return;
//   }
//
//   uint32_t size;
//   coded_input->ReadVarint32(&size);
//
//   char* text = new char[size + 1];
//   coded_input->ReadRaw(buffer, size);
//   text[size] = '\0';
//
//   delete coded_input;
//   delete raw_input;
//   close(fd);
//
//   cout << "Text is: " << text << endl;
//   delete [] text;
//
// For those who are interested, varint encoding is defined as follows:
//
// The encoding operates on unsigned integers of up to 64 bits in length.
// Each byte of the encoded value has the format:
// * bits 0-6: Seven bits of the number being encoded.
// * bit 7: Zero if this is the last byte in the encoding (in which
//   case all remaining bits of the number are zero) or 1 if
//   more bytes follow.
// The first byte contains the least-significant 7 bits of the number, the
// second byte (if present) contains the next-least-significant 7 bits,
// and so on.  So, the binary number 1011000101011 would be encoded in two
// bytes as "10101011 00101100".
//
// In theory, varint could be used to encode integers of any length.
// However, for practicality we set a limit at 64 bits.  The maximum encoded
// length of a number is thus 10 bytes.

#ifndef GOOGLE_PROTOBUF_IO_CODED_STREAM_H__
#define GOOGLE_PROTOBUF_IO_CODED_STREAM_H__


#include <assert.h>

#include <atomic>
#include <climits>
#include <cstddef>
#include <cstring>
#include <limits>
#include <string>
#include <type_traits>
#include <utility>

#if defined(_MSC_VER) && _MSC_VER >= 1300 && !defined(__INTEL_COMPILER)
// If MSVC has "/RTCc" set, it will complain about truncating casts at
// runtime.  This file contains some intentional truncating casts.
#pragma runtime_checks("c", off)
#endif


#include <google/protobuf/stubs/common.h>
#include <google/protobuf/stubs/logging.h>
#include <google/protobuf/stubs/strutil.h>
#include <google/protobuf/port.h>
#include <google/protobuf/stubs/port.h>


// Must be included last.
#include <google/protobuf/port_def.inc>

namespace google {
namespace protobuf {

class DescriptorPool;
class MessageFactory;
class ZeroCopyCodedInputStream;

namespace internal {
void MapTestForceDeterministic();
class EpsCopyByteStream;
}  // namespace internal

namespace io {

// Defined in this file.
class CodedInputStream;
class CodedOutputStream;

// Defined in other files.
class ZeroCopyInputStream;   // zero_copy_stream.h
class ZeroCopyOutputStream;  // zero_copy_stream.h

// Class which reads and decodes binary data which is composed of varint-
// encoded integers and fixed-width pieces.  Wraps a ZeroCopyInputStream.
// Most users will not need to deal with CodedInputStream.
//
// Most methods of CodedInputStream that return a bool return false if an
// underlying I/O error occurs or if the data is malformed.  Once such a
// failure occurs, the CodedInputStream is broken and is no longer useful.
// After a failure, callers also should assume writes to "out" args may have
// occurred, though nothing useful can be determined from those writes.
class PROTOBUF_EXPORT CodedInputStream {
 public:
  // Create a CodedInputStream that reads from the given ZeroCopyInputStream.
  explicit CodedInputStream(ZeroCopyInputStream* input);

  // Create a CodedInputStream that reads from the given flat array.  This is
  // faster than using an ArrayInputStream.  PushLimit(size) is implied by
  // this constructor.
  explicit CodedInputStream(const uint8_t* buffer, int size);

  // Destroy the CodedInputStream and position the underlying
  // ZeroCopyInputStream at the first unread byte.  If an error occurred while
  // reading (causing a method to return false), then the exact position of
  // the input stream may be anywhere between the last value that was read
  // successfully and the stream's byte limit.
  ~CodedInputStream();

  // Return true if this CodedInputStream reads from a flat array instead of
  // a ZeroCopyInputStream.
  inline bool IsFlat() const;

  // Skips a number of bytes.  Returns false if an underlying read error
  // occurs.
  inline bool Skip(int count);

  // Sets *data to point directly at the unread part of the CodedInputStream's
  // underlying buffer, and *size to the size of that buffer, but does not
  // advance the stream's current position.  This will always either produce
  // a non-empty buffer or return false.  If the caller consumes any of
  // this data, it should then call Skip() to skip over the consumed bytes.
  // This may be useful for implementing external fast parsing routines for
  // types of data not covered by the CodedInputStream interface.
  bool GetDirectBufferPointer(const void** data, int* size);

  // Like GetDirectBufferPointer, but this method is inlined, and does not
  // attempt to Refresh() if the buffer is currently empty.
  PROTOBUF_ALWAYS_INLINE
  void GetDirectBufferPointerInline(const void** data, int* size);

  // Read raw bytes, copying them into the given buffer.
  bool ReadRaw(void* buffer, int size);

  // Like ReadRaw, but reads into a string.
  bool ReadString(std::string* buffer, int size);


  // Read a 32-bit little-endian integer.
  bool ReadLittleEndian32(uint32_t* value);
  // Read a 64-bit little-endian integer.
  bool ReadLittleEndian64(uint64_t* value);

  // These methods read from an externally provided buffer. The caller is
  // responsible for ensuring that the buffer has sufficient space.
  // Read a 32-bit little-endian integer.
  static const uint8_t* ReadLittleEndian32FromArray(const uint8_t* buffer,
                                                    uint32_t* value);
  // Read a 64-bit little-endian integer.
  static const uint8_t* ReadLittleEndian64FromArray(const uint8_t* buffer,
                                                    uint64_t* value);

  // Read an unsigned integer with Varint encoding, truncating to 32 bits.
  // Reading a 32-bit value is equivalent to reading a 64-bit one and casting
  // it to uint32_t, but may be more efficient.
  bool ReadVarint32(uint32_t* value);
  // Read an unsigned integer with Varint encoding.
  bool ReadVarint64(uint64_t* value);

  // Reads a varint off the wire into an "int". This should be used for reading
  // sizes off the wire (sizes of strings, submessages, bytes fields, etc).
  //
  // The value from the wire is interpreted as unsigned.  If its value exceeds
  // the representable value of an integer on this platform, instead of
  // truncating we return false. Truncating (as performed by ReadVarint32()
  // above) is an acceptable approach for fields representing an integer, but
  // when we are parsing a size from the wire, truncating the value would result
  // in us misparsing the payload.
  bool ReadVarintSizeAsInt(int* value);

  // Read a tag.  This calls ReadVarint32() and returns the result, or returns
  // zero (which is not a valid tag) if ReadVarint32() fails.  Also, ReadTag
  // (but not ReadTagNoLastTag) updates the last tag value, which can be checked
  // with LastTagWas().
  //
  // Always inline because this is only called in one place per parse loop
  // but it is called for every iteration of said loop, so it should be fast.
  // GCC doesn't want to inline this by default.
  PROTOBUF_ALWAYS_INLINE uint32_t ReadTag() {
    return last_tag_ = ReadTagNoLastTag();
  }

  PROTOBUF_ALWAYS_INLINE uint32_t ReadTagNoLastTag();

  // This usually a faster alternative to ReadTag() when cutoff is a manifest
  // constant.  It does particularly well for cutoff >= 127.  The first part
  // of the return value is the tag that was read, though it can also be 0 in
  // the cases where ReadTag() would return 0.  If the second part is true
  // then the tag is known to be in [0, cutoff].  If not, the tag either is
  // above cutoff or is 0.  (There's intentional wiggle room when tag is 0,
  // because that can arise in several ways, and for best performance we want
  // to avoid an extra "is tag == 0?" check here.)
  PROTOBUF_ALWAYS_INLINE
  std::pair<uint32_t, bool> ReadTagWithCutoff(uint32_t cutoff) {
    std::pair<uint32_t, bool> result = ReadTagWithCutoffNoLastTag(cutoff);
    last_tag_ = result.first;
    return result;
  }

  PROTOBUF_ALWAYS_INLINE
  std::pair<uint32_t, bool> ReadTagWithCutoffNoLastTag(uint32_t cutoff);

  // Usually returns true if calling ReadVarint32() now would produce the given
  // value.  Will always return false if ReadVarint32() would not return the
  // given value.  If ExpectTag() returns true, it also advances past
  // the varint.  For best performance, use a compile-time constant as the
  // parameter.
  // Always inline because this collapses to a small number of instructions
  // when given a constant parameter, but GCC doesn't want to inline by default.
  PROTOBUF_ALWAYS_INLINE bool ExpectTag(uint32_t expected);

  // Like above, except this reads from the specified buffer. The caller is
  // responsible for ensuring that the buffer is large enough to read a varint
  // of the expected size. For best performance, use a compile-time constant as
  // the expected tag parameter.
  //
  // Returns a pointer beyond the expected tag if it was found, or NULL if it
  // was not.
  PROTOBUF_ALWAYS_INLINE
  static const uint8_t* ExpectTagFromArray(const uint8_t* buffer,
                                           uint32_t expected);

  // Usually returns true if no more bytes can be read.  Always returns false
  // if more bytes can be read.  If ExpectAtEnd() returns true, a subsequent
  // call to LastTagWas() will act as if ReadTag() had been called and returned
  // zero, and ConsumedEntireMessage() will return true.
  bool ExpectAtEnd();

  // If the last call to ReadTag() or ReadTagWithCutoff() returned the given
  // value, returns true.  Otherwise, returns false.
  // ReadTagNoLastTag/ReadTagWithCutoffNoLastTag do not preserve the last
  // returned value.
  //
  // This is needed because parsers for some types of embedded messages
  // (with field type TYPE_GROUP) don't actually know that they've reached the
  // end of a message until they see an ENDGROUP tag, which was actually part
  // of the enclosing message.  The enclosing message would like to check that
  // tag to make sure it had the right number, so it calls LastTagWas() on
  // return from the embedded parser to check.
  bool LastTagWas(uint32_t expected);
  void SetLastTag(uint32_t tag) { last_tag_ = tag; }

  // When parsing message (but NOT a group), this method must be called
  // immediately after MergeFromCodedStream() returns (if it returns true)
  // to further verify that the message ended in a legitimate way.  For
  // example, this verifies that parsing did not end on an end-group tag.
  // It also checks for some cases where, due to optimizations,
  // MergeFromCodedStream() can incorrectly return true.
  bool ConsumedEntireMessage();
  void SetConsumed() { legitimate_message_end_ = true; }

  // Limits ----------------------------------------------------------
  // Limits are used when parsing length-delimited embedded messages.
  // After the message's length is read, PushLimit() is used to prevent
  // the CodedInputStream from reading beyond that length.  Once the
  // embedded message has been parsed, PopLimit() is called to undo the
  // limit.

  // Opaque type used with PushLimit() and PopLimit().  Do not modify
  // values of this type yourself.  The only reason that this isn't a
  // struct with private internals is for efficiency.
  typedef int Limit;

  // Places a limit on the number of bytes that the stream may read,
  // starting from the current position.  Once the stream hits this limit,
  // it will act like the end of the input has been reached until PopLimit()
  // is called.
  //
  // As the names imply, the stream conceptually has a stack of limits.  The
  // shortest limit on the stack is always enforced, even if it is not the
  // top limit.
  //
  // The value returned by PushLimit() is opaque to the caller, and must
  // be passed unchanged to the corresponding call to PopLimit().
  Limit PushLimit(int byte_limit);

  // Pops the last limit pushed by PushLimit().  The input must be the value
  // returned by that call to PushLimit().
  void PopLimit(Limit limit);

  // Returns the number of bytes left until the nearest limit on the
  // stack is hit, or -1 if no limits are in place.
  int BytesUntilLimit() const;

  // Returns current position relative to the beginning of the input stream.
  int CurrentPosition() const;

  // Total Bytes Limit -----------------------------------------------
  // To prevent malicious users from sending excessively large messages
  // and causing memory exhaustion, CodedInputStream imposes a hard limit on
  // the total number of bytes it will read.

  // Sets the maximum number of bytes that this CodedInputStream will read
  // before refusing to continue.  To prevent servers from allocating enormous
  // amounts of memory to hold parsed messages, the maximum message length
  // should be limited to the shortest length that will not harm usability.
  // The default limit is INT_MAX (~2GB) and apps should set shorter limits
  // if possible. An error will always be printed to stderr if the limit is
  // reached.
  //
  // Note: setting a limit less than the current read position is interpreted
  // as a limit on the current position.
  //
  // This is unrelated to PushLimit()/PopLimit().
  void SetTotalBytesLimit(int total_bytes_limit);

  // The Total Bytes Limit minus the Current Position, or -1 if the total bytes
  // limit is INT_MAX.
  int BytesUntilTotalBytesLimit() const;

  // Recursion Limit -------------------------------------------------
  // To prevent corrupt or malicious messages from causing stack overflows,
  // we must keep track of the depth of recursion when parsing embedded
  // messages and groups.  CodedInputStream keeps track of this because it
  // is the only object that is passed down the stack during parsing.

  // Sets the maximum recursion depth.  The default is 100.
  void SetRecursionLimit(int limit);
  int RecursionBudget() { return recursion_budget_; }

  static int GetDefaultRecursionLimit() { return default_recursion_limit_; }

  // Increments the current recursion depth.  Returns true if the depth is
  // under the limit, false if it has gone over.
  bool IncrementRecursionDepth();

  // Decrements the recursion depth if possible.
  void DecrementRecursionDepth();

  // Decrements the recursion depth blindly.  This is faster than
  // DecrementRecursionDepth().  It should be used only if all previous
  // increments to recursion depth were successful.
  void UnsafeDecrementRecursionDepth();

  // Shorthand for make_pair(PushLimit(byte_limit), --recursion_budget_).
  // Using this can reduce code size and complexity in some cases.  The caller
  // is expected to check that the second part of the result is non-negative (to
  // bail out if the depth of recursion is too high) and, if all is well, to
  // later pass the first part of the result to PopLimit() or similar.
  std::pair<CodedInputStream::Limit, int> IncrementRecursionDepthAndPushLimit(
      int byte_limit);

  // Shorthand for PushLimit(ReadVarint32(&length) ? length : 0).
  Limit ReadLengthAndPushLimit();

  // Helper that is equivalent to: {
  //  bool result = ConsumedEntireMessage();
  //  PopLimit(limit);
  //  UnsafeDecrementRecursionDepth();
  //  return result; }
  // Using this can reduce code size and complexity in some cases.
  // Do not use unless the current recursion depth is greater than zero.
  bool DecrementRecursionDepthAndPopLimit(Limit limit);

  // Helper that is equivalent to: {
  //  bool result = ConsumedEntireMessage();
  //  PopLimit(limit);
  //  return result; }
  // Using this can reduce code size and complexity in some cases.
  bool CheckEntireMessageConsumedAndPopLimit(Limit limit);

  // Extension Registry ----------------------------------------------
  // ADVANCED USAGE:  99.9% of people can ignore this section.
  //
  // By default, when parsing extensions, the parser looks for extension
  // definitions in the pool which owns the outer message's Descriptor.
  // However, you may call SetExtensionRegistry() to provide an alternative
  // pool instead.  This makes it possible, for example, to parse a message
  // using a generated class, but represent some extensions using
  // DynamicMessage.

  // Set the pool used to look up extensions.  Most users do not need to call
  // this as the correct pool will be chosen automatically.
  //
  // WARNING:  It is very easy to misuse this.  Carefully read the requirements
  //   below.  Do not use this unless you are sure you need it.  Almost no one
  //   does.
  //
  // Let's say you are parsing a message into message object m, and you want
  // to take advantage of SetExtensionRegistry().  You must follow these
  // requirements:
  //
  // The given DescriptorPool must contain m->GetDescriptor().  It is not
  // sufficient for it to simply contain a descriptor that has the same name
  // and content -- it must be the *exact object*.  In other words:
  //   assert(pool->FindMessageTypeByName(m->GetDescriptor()->full_name()) ==
  //          m->GetDescriptor());
  // There are two ways to satisfy this requirement:
  // 1) Use m->GetDescriptor()->pool() as the pool.  This is generally useless
  //    because this is the pool that would be used anyway if you didn't call
  //    SetExtensionRegistry() at all.
  // 2) Use a DescriptorPool which has m->GetDescriptor()->pool() as an
  //    "underlay".  Read the documentation for DescriptorPool for more
  //    information about underlays.
  //
  // You must also provide a MessageFactory.  This factory will be used to
  // construct Message objects representing extensions.  The factory's
  // GetPrototype() MUST return non-NULL for any Descriptor which can be found
  // through the provided pool.
  //
  // If the provided factory might return instances of protocol-compiler-
  // generated (i.e. compiled-in) types, or if the outer message object m is
  // a generated type, then the given factory MUST have this property:  If
  // GetPrototype() is given a Descriptor which resides in
  // DescriptorPool::generated_pool(), the factory MUST return the same
  // prototype which MessageFactory::generated_factory() would return.  That
  // is, given a descriptor for a generated type, the factory must return an
  // instance of the generated class (NOT DynamicMessage).  However, when
  // given a descriptor for a type that is NOT in generated_pool, the factory
  // is free to return any implementation.
  //
  // The reason for this requirement is that generated sub-objects may be
  // accessed via the standard (non-reflection) extension accessor methods,
  // and these methods will down-cast the object to the generated class type.
  // If the object is not actually of that type, the results would be undefined.
  // On the other hand, if an extension is not compiled in, then there is no
  // way the code could end up accessing it via the standard accessors -- the
  // only way to access the extension is via reflection.  When using reflection,
  // DynamicMessage and generated messages are indistinguishable, so it's fine
  // if these objects are represented using DynamicMessage.
  //
  // Using DynamicMessageFactory on which you have called
  // SetDelegateToGeneratedFactory(true) should be sufficient to satisfy the
  // above requirement.
  //
  // If either pool or factory is NULL, both must be NULL.
  //
  // Note that this feature is ignored when parsing "lite" messages as they do
  // not have descriptors.
  void SetExtensionRegistry(const DescriptorPool* pool,
                            MessageFactory* factory);

  // Get the DescriptorPool set via SetExtensionRegistry(), or NULL if no pool
  // has been provided.
  const DescriptorPool* GetExtensionPool();

  // Get the MessageFactory set via SetExtensionRegistry(), or NULL if no
  // factory has been provided.
  MessageFactory* GetExtensionFactory();

 private:
  GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CodedInputStream);

  const uint8_t* buffer_;
  const uint8_t* buffer_end_;  // pointer to the end of the buffer.
  ZeroCopyInputStream* input_;
  int total_bytes_read_;  // total bytes read from input_, including
                          // the current buffer

  // If total_bytes_read_ surpasses INT_MAX, we record the extra bytes here
  // so that we can BackUp() on destruction.
  int overflow_bytes_;

  // LastTagWas() stuff.
  uint32_t last_tag_;  // result of last ReadTag() or ReadTagWithCutoff().

  // This is set true by ReadTag{Fallback/Slow}() if it is called when exactly
  // at EOF, or by ExpectAtEnd() when it returns true.  This happens when we
  // reach the end of a message and attempt to read another tag.
  bool legitimate_message_end_;

  // See EnableAliasing().
  bool aliasing_enabled_;

  // Limits
  Limit current_limit_;  // if position = -1, no limit is applied

  // For simplicity, if the current buffer crosses a limit (either a normal
  // limit created by PushLimit() or the total bytes limit), buffer_size_
  // only tracks the number of bytes before that limit.  This field
  // contains the number of bytes after it.  Note that this implies that if
  // buffer_size_ == 0 and buffer_size_after_limit_ > 0, we know we've
  // hit a limit.  However, if both are zero, it doesn't necessarily mean
  // we aren't at a limit -- the buffer may have ended exactly at the limit.
  int buffer_size_after_limit_;

  // Maximum number of bytes to read, period.  This is unrelated to
  // current_limit_.  Set using SetTotalBytesLimit().
  int total_bytes_limit_;

  // Current recursion budget, controlled by IncrementRecursionDepth() and
  // similar.  Starts at recursion_limit_ and goes down: if this reaches
  // -1 we are over budget.
  int recursion_budget_;
  // Recursion depth limit, set by SetRecursionLimit().
  int recursion_limit_;

  // See SetExtensionRegistry().
  const DescriptorPool* extension_pool_;
  MessageFactory* extension_factory_;

  // Private member functions.

  // Fallback when Skip() goes past the end of the current buffer.
  bool SkipFallback(int count, int original_buffer_size);

  // Advance the buffer by a given number of bytes.
  void Advance(int amount);

  // Back up input_ to the current buffer position.
  void BackUpInputToCurrentPosition();

  // Recomputes the value of buffer_size_after_limit_.  Must be called after
  // current_limit_ or total_bytes_limit_ changes.
  void RecomputeBufferLimits();

  // Writes an error message saying that we hit total_bytes_limit_.
  void PrintTotalBytesLimitError();

  // Called when the buffer runs out to request more data.  Implies an
  // Advance(BufferSize()).
  bool Refresh();

  // When parsing varints, we optimize for the common case of small values, and
  // then optimize for the case when the varint fits within the current buffer
  // piece. The Fallback method is used when we can't use the one-byte
  // optimization. The Slow method is yet another fallback when the buffer is
  // not large enough. Making the slow path out-of-line speeds up the common
  // case by 10-15%. The slow path is fairly uncommon: it only triggers when a
  // message crosses multiple buffers.  Note: ReadVarint32Fallback() and
  // ReadVarint64Fallback() are called frequently and generally not inlined, so
  // they have been optimized to avoid "out" parameters.  The former returns -1
  // if it fails and the uint32_t it read otherwise.  The latter has a bool
  // indicating success or failure as part of its return type.
  int64_t ReadVarint32Fallback(uint32_t first_byte_or_zero);
  int ReadVarintSizeAsIntFallback();
  std::pair<uint64_t, bool> ReadVarint64Fallback();
  bool ReadVarint32Slow(uint32_t* value);
  bool ReadVarint64Slow(uint64_t* value);
  int ReadVarintSizeAsIntSlow();
  bool ReadLittleEndian32Fallback(uint32_t* value);
  bool ReadLittleEndian64Fallback(uint64_t* value);

  // Fallback/slow methods for reading tags. These do not update last_tag_,
  // but will set legitimate_message_end_ if we are at the end of the input
  // stream.
  uint32_t ReadTagFallback(uint32_t first_byte_or_zero);
  uint32_t ReadTagSlow();
  bool ReadStringFallback(std::string* buffer, int size);

  // Return the size of the buffer.
  int BufferSize() const;

  static const int kDefaultTotalBytesLimit = INT_MAX;

  static int default_recursion_limit_;  // 100 by default.

  friend class google::protobuf::ZeroCopyCodedInputStream;
  friend class google::protobuf::internal::EpsCopyByteStream;
};

// EpsCopyOutputStream wraps a ZeroCopyOutputStream and exposes a new stream,
// which has the property you can write kSlopBytes (16 bytes) from the current
// position without bounds checks. The cursor into the stream is managed by
// the user of the class and is an explicit parameter in the methods. Careful
// use of this class, ie. keep ptr a local variable, eliminates the need to
// for the compiler to sync the ptr value between register and memory.
class PROTOBUF_EXPORT EpsCopyOutputStream {
 public:
  enum { kSlopBytes = 16 };

  // Initialize from a stream.
  EpsCopyOutputStream(ZeroCopyOutputStream* stream, bool deterministic,
                      uint8_t** pp)
      : end_(buffer_),
        stream_(stream),
        is_serialization_deterministic_(deterministic) {
    *pp = buffer_;
  }

  // Only for array serialization. No overflow protection, end_ will be the
  // pointed to the end of the array. When using this the total size is already
  // known, so no need to maintain the slop region.
  EpsCopyOutputStream(void* data, int size, bool deterministic)
      : end_(static_cast<uint8_t*>(data) + size),
        buffer_end_(nullptr),
        stream_(nullptr),
        is_serialization_deterministic_(deterministic) {}

  // Initialize from stream but with the first buffer already given (eager).
  EpsCopyOutputStream(void* data, int size, ZeroCopyOutputStream* stream,
                      bool deterministic, uint8_t** pp)
      : stream_(stream), is_serialization_deterministic_(deterministic) {
    *pp = SetInitialBuffer(data, size);
  }

  // Flush everything that's written into the underlying ZeroCopyOutputStream
  // and trims the underlying stream to the location of ptr.
  uint8_t* Trim(uint8_t* ptr);

  // After this it's guaranteed you can safely write kSlopBytes to ptr. This
  // will never fail! The underlying stream can produce an error. Use HadError
  // to check for errors.
  PROTOBUF_NODISCARD uint8_t* EnsureSpace(uint8_t* ptr) {
    if (PROTOBUF_PREDICT_FALSE(ptr >= end_)) {
      return EnsureSpaceFallback(ptr);
    }
    return ptr;
  }

  uint8_t* WriteRaw(const void* data, int size, uint8_t* ptr) {
    if (PROTOBUF_PREDICT_FALSE(end_ - ptr < size)) {
      return WriteRawFallback(data, size, ptr);
    }
    std::memcpy(ptr, data, size);
    return ptr + size;
  }
  // Writes the buffer specified by data, size to the stream. Possibly by
  // aliasing the buffer (ie. not copying the data). The caller is responsible
  // to make sure the buffer is alive for the duration of the
  // ZeroCopyOutputStream.
#ifndef NDEBUG
  PROTOBUF_NOINLINE
#endif
  uint8_t* WriteRawMaybeAliased(const void* data, int size, uint8_t* ptr) {
    if (aliasing_enabled_) {
      return WriteAliasedRaw(data, size, ptr);
    } else {
      return WriteRaw(data, size, ptr);
    }
  }


#ifndef NDEBUG
  PROTOBUF_NOINLINE
#endif
  uint8_t* WriteStringMaybeAliased(uint32_t num, const std::string& s,
                                   uint8_t* ptr) {
    std::ptrdiff_t size = s.size();
    if (PROTOBUF_PREDICT_FALSE(
            size >= 128 || end_ - ptr + 16 - TagSize(num << 3) - 1 < size)) {
      return WriteStringMaybeAliasedOutline(num, s, ptr);
    }
    ptr = UnsafeVarint((num << 3) | 2, ptr);
    *ptr++ = static_cast<uint8_t>(size);
    std::memcpy(ptr, s.data(), size);
    return ptr + size;
  }
  uint8_t* WriteBytesMaybeAliased(uint32_t num, const std::string& s,
                                  uint8_t* ptr) {
    return WriteStringMaybeAliased(num, s, ptr);
  }

  template <typename T>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteString(uint32_t num, const T& s,
                                              uint8_t* ptr) {
    std::ptrdiff_t size = s.size();
    if (PROTOBUF_PREDICT_FALSE(
            size >= 128 || end_ - ptr + 16 - TagSize(num << 3) - 1 < size)) {
      return WriteStringOutline(num, s, ptr);
    }
    ptr = UnsafeVarint((num << 3) | 2, ptr);
    *ptr++ = static_cast<uint8_t>(size);
    std::memcpy(ptr, s.data(), size);
    return ptr + size;
  }
  template <typename T>
#ifndef NDEBUG
  PROTOBUF_NOINLINE
#endif
  uint8_t* WriteBytes(uint32_t num, const T& s, uint8_t* ptr) {
    return WriteString(num, s, ptr);
  }

  template <typename T>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteInt32Packed(int num, const T& r,
                                                   int size, uint8_t* ptr) {
    return WriteVarintPacked(num, r, size, ptr, Encode64);
  }
  template <typename T>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteUInt32Packed(int num, const T& r,
                                                    int size, uint8_t* ptr) {
    return WriteVarintPacked(num, r, size, ptr, Encode32);
  }
  template <typename T>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteSInt32Packed(int num, const T& r,
                                                    int size, uint8_t* ptr) {
    return WriteVarintPacked(num, r, size, ptr, ZigZagEncode32);
  }
  template <typename T>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteInt64Packed(int num, const T& r,
                                                   int size, uint8_t* ptr) {
    return WriteVarintPacked(num, r, size, ptr, Encode64);
  }
  template <typename T>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteUInt64Packed(int num, const T& r,
                                                    int size, uint8_t* ptr) {
    return WriteVarintPacked(num, r, size, ptr, Encode64);
  }
  template <typename T>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteSInt64Packed(int num, const T& r,
                                                    int size, uint8_t* ptr) {
    return WriteVarintPacked(num, r, size, ptr, ZigZagEncode64);
  }
  template <typename T>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteEnumPacked(int num, const T& r, int size,
                                                  uint8_t* ptr) {
    return WriteVarintPacked(num, r, size, ptr, Encode64);
  }

  template <typename T>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteFixedPacked(int num, const T& r,
                                                   uint8_t* ptr) {
    ptr = EnsureSpace(ptr);
    constexpr auto element_size = sizeof(typename T::value_type);
    auto size = r.size() * element_size;
    ptr = WriteLengthDelim(num, size, ptr);
    return WriteRawLittleEndian<element_size>(r.data(), static_cast<int>(size),
                                              ptr);
  }

  // Returns true if there was an underlying I/O error since this object was
  // created.
  bool HadError() const { return had_error_; }

  // Instructs the EpsCopyOutputStream to allow the underlying
  // ZeroCopyOutputStream to hold pointers to the original structure instead of
  // copying, if it supports it (i.e. output->AllowsAliasing() is true).  If the
  // underlying stream does not support aliasing, then enabling it has no
  // affect.  For now, this only affects the behavior of
  // WriteRawMaybeAliased().
  //
  // NOTE: It is caller's responsibility to ensure that the chunk of memory
  // remains live until all of the data has been consumed from the stream.
  void EnableAliasing(bool enabled);

  // See documentation on CodedOutputStream::SetSerializationDeterministic.
  void SetSerializationDeterministic(bool value) {
    is_serialization_deterministic_ = value;
  }

  // See documentation on CodedOutputStream::IsSerializationDeterministic.
  bool IsSerializationDeterministic() const {
    return is_serialization_deterministic_;
  }

  // The number of bytes written to the stream at position ptr, relative to the
  // stream's overall position.
  int64_t ByteCount(uint8_t* ptr) const;


 private:
  uint8_t* end_;
  uint8_t* buffer_end_ = buffer_;
  uint8_t buffer_[2 * kSlopBytes];
  ZeroCopyOutputStream* stream_;
  bool had_error_ = false;
  bool aliasing_enabled_ = false;  // See EnableAliasing().
  bool is_serialization_deterministic_;
  bool skip_check_consistency = false;

  uint8_t* EnsureSpaceFallback(uint8_t* ptr);
  inline uint8_t* Next();
  int Flush(uint8_t* ptr);
  std::ptrdiff_t GetSize(uint8_t* ptr) const {
    GOOGLE_DCHECK(ptr <= end_ + kSlopBytes);  // NOLINT
    return end_ + kSlopBytes - ptr;
  }

  uint8_t* Error() {
    had_error_ = true;
    // We use the patch buffer to always guarantee space to write to.
    end_ = buffer_ + kSlopBytes;
    return buffer_;
  }

  static constexpr int TagSize(uint32_t tag) {
    return (tag < (1 << 7))    ? 1
           : (tag < (1 << 14)) ? 2
           : (tag < (1 << 21)) ? 3
           : (tag < (1 << 28)) ? 4
                               : 5;
  }

  PROTOBUF_ALWAYS_INLINE uint8_t* WriteTag(uint32_t num, uint32_t wt,
                                           uint8_t* ptr) {
    GOOGLE_DCHECK(ptr < end_);  // NOLINT
    return UnsafeVarint((num << 3) | wt, ptr);
  }

  PROTOBUF_ALWAYS_INLINE uint8_t* WriteLengthDelim(int num, uint32_t size,
                                                   uint8_t* ptr) {
    ptr = WriteTag(num, 2, ptr);
    return UnsafeWriteSize(size, ptr);
  }

  uint8_t* WriteRawFallback(const void* data, int size, uint8_t* ptr);

  uint8_t* WriteAliasedRaw(const void* data, int size, uint8_t* ptr);

  uint8_t* WriteStringMaybeAliasedOutline(uint32_t num, const std::string& s,
                                          uint8_t* ptr);
  uint8_t* WriteStringOutline(uint32_t num, const std::string& s, uint8_t* ptr);

  template <typename T, typename E>
  PROTOBUF_ALWAYS_INLINE uint8_t* WriteVarintPacked(int num, const T& r,
                                                    int size, uint8_t* ptr,
                                                    const E& encode) {
    ptr = EnsureSpace(ptr);
    ptr = WriteLengthDelim(num, size, ptr);
    auto it = r.data();
    auto end = it + r.size();
    do {
      ptr = EnsureSpace(ptr);
      ptr = UnsafeVarint(encode(*it++), ptr);
    } while (it < end);
    return ptr;
  }

  static uint32_t Encode32(uint32_t v) { return v; }
  static uint64_t Encode64(uint64_t v) { return v; }
  static uint32_t ZigZagEncode32(int32_t v) {
    return (static_cast<uint32_t>(v) << 1) ^ static_cast<uint32_t>(v >> 31);
  }
  static uint64_t ZigZagEncode64(int64_t v) {
    return (static_cast<uint64_t>(v) << 1) ^ static_cast<uint64_t>(v >> 63);
  }

  template <typename T>
  PROTOBUF_ALWAYS_INLINE static uint8_t* UnsafeVarint(T value, uint8_t* ptr) {
    static_assert(std::is_unsigned<T>::value,
                  "Varint serialization must be unsigned");
    ptr[0] = static_cast<uint8_t>(value);
    if (value < 0x80) {
      return ptr + 1;
    }
    // Turn on continuation bit in the byte we just wrote.
    ptr[0] |= static_cast<uint8_t>(0x80);
    value >>= 7;
    ptr[1] = static_cast<uint8_t>(value);
    if (value < 0x80) {
      return ptr + 2;
    }
    ptr += 2;
    do {
      // Turn on continuation bit in the byte we just wrote.
      ptr[-1] |= static_cast<uint8_t>(0x80);
      value >>= 7;
      *ptr = static_cast<uint8_t>(value);
      ++ptr;
    } while (value >= 0x80);
    return ptr;
  }

  PROTOBUF_ALWAYS_INLINE static uint8_t* UnsafeWriteSize(uint32_t value,
                                                         uint8_t* ptr) {
    while (PROTOBUF_PREDICT_FALSE(value >= 0x80)) {
      *ptr = static_cast<uint8_t>(value | 0x80);
      value >>= 7;
      ++ptr;
    }
    *ptr++ = static_cast<uint8_t>(value);
    return ptr;
  }

  template <int S>
  uint8_t* WriteRawLittleEndian(const void* data, int size, uint8_t* ptr);
#if !defined(PROTOBUF_LITTLE_ENDIAN) || \
    defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
  uint8_t* WriteRawLittleEndian32(const void* data, int size, uint8_t* ptr);
  uint8_t* WriteRawLittleEndian64(const void* data, int size, uint8_t* ptr);
#endif

  // These methods are for CodedOutputStream. Ideally they should be private
  // but to match current behavior of CodedOutputStream as close as possible
  // we allow it some functionality.
 public:
  uint8_t* SetInitialBuffer(void* data, int size) {
    auto ptr = static_cast<uint8_t*>(data);
    if (size > kSlopBytes) {
      end_ = ptr + size - kSlopBytes;
      buffer_end_ = nullptr;
      return ptr;
    } else {
      end_ = buffer_ + size;
      buffer_end_ = ptr;
      return buffer_;
    }
  }

 private:
  // Needed by CodedOutputStream HadError. HadError needs to flush the patch
  // buffers to ensure there is no error as of yet.
  uint8_t* FlushAndResetBuffer(uint8_t*);

  // The following functions mimic the old CodedOutputStream behavior as close
  // as possible. They flush the current state to the stream, behave as
  // the old CodedOutputStream and then return to normal operation.
  bool Skip(int count, uint8_t** pp);
  bool GetDirectBufferPointer(void** data, int* size, uint8_t** pp);
  uint8_t* GetDirectBufferForNBytesAndAdvance(int size, uint8_t** pp);

  friend class CodedOutputStream;
};

template <>
inline uint8_t* EpsCopyOutputStream::WriteRawLittleEndian<1>(const void* data,
                                                             int size,
                                                             uint8_t* ptr) {
  return WriteRaw(data, size, ptr);
}
template <>
inline uint8_t* EpsCopyOutputStream::WriteRawLittleEndian<4>(const void* data,
                                                             int size,
                                                             uint8_t* ptr) {
#if defined(PROTOBUF_LITTLE_ENDIAN) && \
    !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
  return WriteRaw(data, size, ptr);
#else
  return WriteRawLittleEndian32(data, size, ptr);
#endif
}
template <>
inline uint8_t* EpsCopyOutputStream::WriteRawLittleEndian<8>(const void* data,
                                                             int size,
                                                             uint8_t* ptr) {
#if defined(PROTOBUF_LITTLE_ENDIAN) && \
    !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
  return WriteRaw(data, size, ptr);
#else
  return WriteRawLittleEndian64(data, size, ptr);
#endif
}

// Class which encodes and writes binary data which is composed of varint-
// encoded integers and fixed-width pieces.  Wraps a ZeroCopyOutputStream.
// Most users will not need to deal with CodedOutputStream.
//
// Most methods of CodedOutputStream which return a bool return false if an
// underlying I/O error occurs.  Once such a failure occurs, the
// CodedOutputStream is broken and is no longer useful. The Write* methods do
// not return the stream status, but will invalidate the stream if an error
// occurs. The client can probe HadError() to determine the status.
//
// Note that every method of CodedOutputStream which writes some data has
// a corresponding static "ToArray" version. These versions write directly
// to the provided buffer, returning a pointer past the last written byte.
// They require that the buffer has sufficient capacity for the encoded data.
// This allows an optimization where we check if an output stream has enough
// space for an entire message before we start writing and, if there is, we
// call only the ToArray methods to avoid doing bound checks for each
// individual value.
// i.e., in the example above:
//
//   CodedOutputStream* coded_output = new CodedOutputStream(raw_output);
//   int magic_number = 1234;
//   char text[] = "Hello world!";
//
//   int coded_size = sizeof(magic_number) +
//                    CodedOutputStream::VarintSize32(strlen(text)) +
//                    strlen(text);
//
//   uint8_t* buffer =
//       coded_output->GetDirectBufferForNBytesAndAdvance(coded_size);
//   if (buffer != nullptr) {
//     // The output stream has enough space in the buffer: write directly to
//     // the array.
//     buffer = CodedOutputStream::WriteLittleEndian32ToArray(magic_number,
//                                                            buffer);
//     buffer = CodedOutputStream::WriteVarint32ToArray(strlen(text), buffer);
//     buffer = CodedOutputStream::WriteRawToArray(text, strlen(text), buffer);
//   } else {
//     // Make bound-checked writes, which will ask the underlying stream for
//     // more space as needed.
//     coded_output->WriteLittleEndian32(magic_number);
//     coded_output->WriteVarint32(strlen(text));
//     coded_output->WriteRaw(text, strlen(text));
//   }
//
//   delete coded_output;
class PROTOBUF_EXPORT CodedOutputStream {
 public:
  // Creates a CodedOutputStream that writes to the given `stream`.
  // The provided stream must publicly derive from `ZeroCopyOutputStream`.
  template <class Stream, class = typename std::enable_if<std::is_base_of<
                              ZeroCopyOutputStream, Stream>::value>::type>
  explicit CodedOutputStream(Stream* stream);

  // Creates a CodedOutputStream that writes to the given `stream`, and does
  // an 'eager initialization' of the internal state if `eager_init` is true.
  // The provided stream must publicly derive from `ZeroCopyOutputStream`.
  template <class Stream, class = typename std::enable_if<std::is_base_of<
                              ZeroCopyOutputStream, Stream>::value>::type>
  CodedOutputStream(Stream* stream, bool eager_init);

  // Destroy the CodedOutputStream and position the underlying
  // ZeroCopyOutputStream immediately after the last byte written.
  ~CodedOutputStream();

  // Returns true if there was an underlying I/O error since this object was
  // created. On should call Trim before this function in order to catch all
  // errors.
  bool HadError() {
    cur_ = impl_.FlushAndResetBuffer(cur_);
    GOOGLE_DCHECK(cur_);
    return impl_.HadError();
  }

  // Trims any unused space in the underlying buffer so that its size matches
  // the number of bytes written by this stream. The underlying buffer will
  // automatically be trimmed when this stream is destroyed; this call is only
  // necessary if the underlying buffer is accessed *before* the stream is
  // destroyed.
  void Trim() { cur_ = impl_.Trim(cur_); }

  // Skips a number of bytes, leaving the bytes unmodified in the underlying
  // buffer.  Returns false if an underlying write error occurs.  This is
  // mainly useful with GetDirectBufferPointer().
  // Note of caution, the skipped bytes may contain uninitialized data. The
  // caller must make sure that the skipped bytes are properly initialized,
  // otherwise you might leak bytes from your heap.
  bool Skip(int count) { return impl_.Skip(count, &cur_); }

  // Sets *data to point directly at the unwritten part of the
  // CodedOutputStream's underlying buffer, and *size to the size of that
  // buffer, but does not advance the stream's current position.  This will
  // always either produce a non-empty buffer or return false.  If the caller
  // writes any data to this buffer, it should then call Skip() to skip over
  // the consumed bytes.  This may be useful for implementing external fast
  // serialization routines for types of data not covered by the
  // CodedOutputStream interface.
  bool GetDirectBufferPointer(void** data, int* size) {
    return impl_.GetDirectBufferPointer(data, size, &cur_);
  }

  // If there are at least "size" bytes available in the current buffer,
  // returns a pointer directly into the buffer and advances over these bytes.
  // The caller may then write directly into this buffer (e.g. using the
  // *ToArray static methods) rather than go through CodedOutputStream.  If
  // there are not enough bytes available, returns NULL.  The return pointer is
  // invalidated as soon as any other non-const method of CodedOutputStream
  // is called.
  inline uint8_t* GetDirectBufferForNBytesAndAdvance(int size) {
    return impl_.GetDirectBufferForNBytesAndAdvance(size, &cur_);
  }

  // Write raw bytes, copying them from the given buffer.
  void WriteRaw(const void* buffer, int size) {
    cur_ = impl_.WriteRaw(buffer, size, cur_);
  }
  // Like WriteRaw()  but will try to write aliased data if aliasing is
  // turned on.
  void WriteRawMaybeAliased(const void* data, int size);
  // Like WriteRaw()  but writing directly to the target array.
  // This is _not_ inlined, as the compiler often optimizes memcpy into inline
  // copy loops. Since this gets called by every field with string or bytes
  // type, inlining may lead to a significant amount of code bloat, with only a
  // minor performance gain.
  static uint8_t* WriteRawToArray(const void* buffer, int size,
                                  uint8_t* target);

  // Equivalent to WriteRaw(str.data(), str.size()).
  void WriteString(const std::string& str);
  // Like WriteString()  but writing directly to the target array.
  static uint8_t* WriteStringToArray(const std::string& str, uint8_t* target);
  // Write the varint-encoded size of str followed by str.
  static uint8_t* WriteStringWithSizeToArray(const std::string& str,
                                             uint8_t* target);


  // Write a 32-bit little-endian integer.
  void WriteLittleEndian32(uint32_t value) {
    cur_ = impl_.EnsureSpace(cur_);
    SetCur(WriteLittleEndian32ToArray(value, Cur()));
  }
  // Like WriteLittleEndian32()  but writing directly to the target array.
  static uint8_t* WriteLittleEndian32ToArray(uint32_t value, uint8_t* target);
  // Write a 64-bit little-endian integer.
  void WriteLittleEndian64(uint64_t value) {
    cur_ = impl_.EnsureSpace(cur_);
    SetCur(WriteLittleEndian64ToArray(value, Cur()));
  }
  // Like WriteLittleEndian64()  but writing directly to the target array.
  static uint8_t* WriteLittleEndian64ToArray(uint64_t value, uint8_t* target);

  // Write an unsigned integer with Varint encoding.  Writing a 32-bit value
  // is equivalent to casting it to uint64_t and writing it as a 64-bit value,
  // but may be more efficient.
  void WriteVarint32(uint32_t value);
  // Like WriteVarint32()  but writing directly to the target array.
  static uint8_t* WriteVarint32ToArray(uint32_t value, uint8_t* target);
  // Like WriteVarint32()  but writing directly to the target array, and with
  // the less common-case paths being out of line rather than inlined.
  static uint8_t* WriteVarint32ToArrayOutOfLine(uint32_t value,
                                                uint8_t* target);
  // Write an unsigned integer with Varint encoding.
  void WriteVarint64(uint64_t value);
  // Like WriteVarint64()  but writing directly to the target array.
  static uint8_t* WriteVarint64ToArray(uint64_t value, uint8_t* target);

  // Equivalent to WriteVarint32() except when the value is negative,
  // in which case it must be sign-extended to a full 10 bytes.
  void WriteVarint32SignExtended(int32_t value);
  // Like WriteVarint32SignExtended()  but writing directly to the target array.
  static uint8_t* WriteVarint32SignExtendedToArray(int32_t value,
                                                   uint8_t* target);

  // This is identical to WriteVarint32(), but optimized for writing tags.
  // In particular, if the input is a compile-time constant, this method
  // compiles down to a couple instructions.
  // Always inline because otherwise the aforementioned optimization can't work,
  // but GCC by default doesn't want to inline this.
  void WriteTag(uint32_t value);
  // Like WriteTag()  but writing directly to the target array.
  PROTOBUF_ALWAYS_INLINE
  static uint8_t* WriteTagToArray(uint32_t value, uint8_t* target);

  // Returns the number of bytes needed to encode the given value as a varint.
  static size_t VarintSize32(uint32_t value);
  // Returns the number of bytes needed to encode the given value as a varint.
  static size_t VarintSize64(uint64_t value);

  // If negative, 10 bytes.  Otherwise, same as VarintSize32().
  static size_t VarintSize32SignExtended(int32_t value);

  // Same as above, plus one.  The additional one comes at no compute cost.
  static size_t VarintSize32PlusOne(uint32_t value);
  static size_t VarintSize64PlusOne(uint64_t value);
  static size_t VarintSize32SignExtendedPlusOne(int32_t value);

  // Compile-time equivalent of VarintSize32().
  template <uint32_t Value>
  struct StaticVarintSize32 {
    static const size_t value = (Value < (1 << 7))    ? 1
                                : (Value < (1 << 14)) ? 2
                                : (Value < (1 << 21)) ? 3
                                : (Value < (1 << 28)) ? 4
                                                      : 5;
  };

  // Returns the total number of bytes written since this object was created.
  int ByteCount() const {
    return static_cast<int>(impl_.ByteCount(cur_) - start_count_);
  }

  // Instructs the CodedOutputStream to allow the underlying
  // ZeroCopyOutputStream to hold pointers to the original structure instead of
  // copying, if it supports it (i.e. output->AllowsAliasing() is true).  If the
  // underlying stream does not support aliasing, then enabling it has no
  // affect.  For now, this only affects the behavior of
  // WriteRawMaybeAliased().
  //
  // NOTE: It is caller's responsibility to ensure that the chunk of memory
  // remains live until all of the data has been consumed from the stream.
  void EnableAliasing(bool enabled) { impl_.EnableAliasing(enabled); }

  // Indicate to the serializer whether the user wants deterministic
  // serialization. The default when this is not called comes from the global
  // default, controlled by SetDefaultSerializationDeterministic.
  //
  // What deterministic serialization means is entirely up to the driver of the
  // serialization process (i.e. the caller of methods like WriteVarint32). In
  // the case of serializing a proto buffer message using one of the methods of
  // MessageLite, this means that for a given binary equal messages will always
  // be serialized to the same bytes. This implies:
  //
  //   * Repeated serialization of a message will return the same bytes.
  //
  //   * Different processes running the same binary (including on different
  //     machines) will serialize equal messages to the same bytes.
  //
  // Note that this is *not* canonical across languages. It is also unstable
  // across different builds with intervening message definition changes, due to
  // unknown fields. Users who need canonical serialization (e.g. persistent
  // storage in a canonical form, fingerprinting) should define their own
  // canonicalization specification and implement the serializer using
  // reflection APIs rather than relying on this API.
  void SetSerializationDeterministic(bool value) {
    impl_.SetSerializationDeterministic(value);
  }

  // Return whether the user wants deterministic serialization. See above.
  bool IsSerializationDeterministic() const {
    return impl_.IsSerializationDeterministic();
  }

  static bool IsDefaultSerializationDeterministic() {
    return default_serialization_deterministic_.load(
               std::memory_order_relaxed) != 0;
  }

  template <typename Func>
  void Serialize(const Func& func);

  uint8_t* Cur() const { return cur_; }
  void SetCur(uint8_t* ptr) { cur_ = ptr; }
  EpsCopyOutputStream* EpsCopy() { return &impl_; }

 private:
  template <class Stream>
  void InitEagerly(Stream* stream);

  EpsCopyOutputStream impl_;
  uint8_t* cur_;
  int64_t start_count_;
  static std::atomic<bool> default_serialization_deterministic_;

  // See above.  Other projects may use "friend" to allow them to call this.
  // After SetDefaultSerializationDeterministic() completes, all protocol
  // buffer serializations will be deterministic by default.  Thread safe.
  // However, the meaning of "after" is subtle here: to be safe, each thread
  // that wants deterministic serialization by default needs to call
  // SetDefaultSerializationDeterministic() or ensure on its own that another
  // thread has done so.
  friend void internal::MapTestForceDeterministic();
  static void SetDefaultSerializationDeterministic() {
    default_serialization_deterministic_.store(true, std::memory_order_relaxed);
  }
  // REQUIRES: value >= 0x80, and that (value & 7f) has been written to *target.
  static uint8_t* WriteVarint32ToArrayOutOfLineHelper(uint32_t value,
                                                      uint8_t* target);
  GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CodedOutputStream);
};

// inline methods ====================================================
// The vast majority of varints are only one byte.  These inline
// methods optimize for that case.

inline bool CodedInputStream::ReadVarint32(uint32_t* value) {
  uint32_t v = 0;
  if (PROTOBUF_PREDICT_TRUE(buffer_ < buffer_end_)) {
    v = *buffer_;
    if (v < 0x80) {
      *value = v;
      Advance(1);
      return true;
    }
  }
  int64_t result = ReadVarint32Fallback(v);
  *value = static_cast<uint32_t>(result);
  return result >= 0;
}

inline bool CodedInputStream::ReadVarint64(uint64_t* value) {
  if (PROTOBUF_PREDICT_TRUE(buffer_ < buffer_end_) && *buffer_ < 0x80) {
    *value = *buffer_;
    Advance(1);
    return true;
  }
  std::pair<uint64_t, bool> p = ReadVarint64Fallback();
  *value = p.first;
  return p.second;
}

inline bool CodedInputStream::ReadVarintSizeAsInt(int* value) {
  if (PROTOBUF_PREDICT_TRUE(buffer_ < buffer_end_)) {
    int v = *buffer_;
    if (v < 0x80) {
      *value = v;
      Advance(1);
      return true;
    }
  }
  *value = ReadVarintSizeAsIntFallback();
  return *value >= 0;
}

// static
inline const uint8_t* CodedInputStream::ReadLittleEndian32FromArray(
    const uint8_t* buffer, uint32_t* value) {
#if defined(PROTOBUF_LITTLE_ENDIAN) && \
    !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
  memcpy(value, buffer, sizeof(*value));
  return buffer + sizeof(*value);
#else
  *value = (static_cast<uint32_t>(buffer[0])) |
           (static_cast<uint32_t>(buffer[1]) << 8) |
           (static_cast<uint32_t>(buffer[2]) << 16) |
           (static_cast<uint32_t>(buffer[3]) << 24);
  return buffer + sizeof(*value);
#endif
}
// static
inline const uint8_t* CodedInputStream::ReadLittleEndian64FromArray(
    const uint8_t* buffer, uint64_t* value) {
#if defined(PROTOBUF_LITTLE_ENDIAN) && \
    !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
  memcpy(value, buffer, sizeof(*value));
  return buffer + sizeof(*value);
#else
  uint32_t part0 = (static_cast<uint32_t>(buffer[0])) |
                   (static_cast<uint32_t>(buffer[1]) << 8) |
                   (static_cast<uint32_t>(buffer[2]) << 16) |
                   (static_cast<uint32_t>(buffer[3]) << 24);
  uint32_t part1 = (static_cast<uint32_t>(buffer[4])) |
                   (static_cast<uint32_t>(buffer[5]) << 8) |
                   (static_cast<uint32_t>(buffer[6]) << 16) |
                   (static_cast<uint32_t>(buffer[7]) << 24);
  *value = static_cast<uint64_t>(part0) | (static_cast<uint64_t>(part1) << 32);
  return buffer + sizeof(*value);
#endif
}

inline bool CodedInputStream::ReadLittleEndian32(uint32_t* value) {
#if defined(PROTOBUF_LITTLE_ENDIAN) && \
    !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
  if (PROTOBUF_PREDICT_TRUE(BufferSize() >= static_cast<int>(sizeof(*value)))) {
    buffer_ = ReadLittleEndian32FromArray(buffer_, value);
    return true;
  } else {
    return ReadLittleEndian32Fallback(value);
  }
#else
  return ReadLittleEndian32Fallback(value);
#endif
}

inline bool CodedInputStream::ReadLittleEndian64(uint64_t* value) {
#if defined(PROTOBUF_LITTLE_ENDIAN) && \
    !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
  if (PROTOBUF_PREDICT_TRUE(BufferSize() >= static_cast<int>(sizeof(*value)))) {
    buffer_ = ReadLittleEndian64FromArray(buffer_, value);
    return true;
  } else {
    return ReadLittleEndian64Fallback(value);
  }
#else
  return ReadLittleEndian64Fallback(value);
#endif
}

inline uint32_t CodedInputStream::ReadTagNoLastTag() {
  uint32_t v = 0;
  if (PROTOBUF_PREDICT_TRUE(buffer_ < buffer_end_)) {
    v = *buffer_;
    if (v < 0x80) {
      Advance(1);
      return v;
    }
  }
  v = ReadTagFallback(v);
  return v;
}

inline std::pair<uint32_t, bool> CodedInputStream::ReadTagWithCutoffNoLastTag(
    uint32_t cutoff) {
  // In performance-sensitive code we can expect cutoff to be a compile-time
  // constant, and things like "cutoff >= kMax1ByteVarint" to be evaluated at
  // compile time.
  uint32_t first_byte_or_zero = 0;
  if (PROTOBUF_PREDICT_TRUE(buffer_ < buffer_end_)) {
    // Hot case: buffer_ non_empty, buffer_[0] in [1, 128).
    // TODO(gpike): Is it worth rearranging this? E.g., if the number of fields
    // is large enough then is it better to check for the two-byte case first?
    first_byte_or_zero = buffer_[0];
    if (static_cast<int8_t>(buffer_[0]) > 0) {
      const uint32_t kMax1ByteVarint = 0x7f;
      uint32_t tag = buffer_[0];
      Advance(1);
      return std::make_pair(tag, cutoff >= kMax1ByteVarint || tag <= cutoff);
    }
    // Other hot case: cutoff >= 0x80, buffer_ has at least two bytes available,
    // and tag is two bytes.  The latter is tested by bitwise-and-not of the
    // first byte and the second byte.
    if (cutoff >= 0x80 && PROTOBUF_PREDICT_TRUE(buffer_ + 1 < buffer_end_) &&
        PROTOBUF_PREDICT_TRUE((buffer_[0] & ~buffer_[1]) >= 0x80)) {
      const uint32_t kMax2ByteVarint = (0x7f << 7) + 0x7f;
      uint32_t tag = (1u << 7) * buffer_[1] + (buffer_[0] - 0x80);
      Advance(2);
      // It might make sense to test for tag == 0 now, but it is so rare that
      // that we don't bother.  A varint-encoded 0 should be one byte unless
      // the encoder lost its mind.  The second part of the return value of
      // this function is allowed to be either true or false if the tag is 0,
      // so we don't have to check for tag == 0.  We may need to check whether
      // it exceeds cutoff.
      bool at_or_below_cutoff = cutoff >= kMax2ByteVarint || tag <= cutoff;
      return std::make_pair(tag, at_or_below_cutoff);
    }
  }
  // Slow path
  const uint32_t tag = ReadTagFallback(first_byte_or_zero);
  return std::make_pair(tag, static_cast<uint32_t>(tag - 1) < cutoff);
}

inline bool CodedInputStream::LastTagWas(uint32_t expected) {
  return last_tag_ == expected;
}

inline bool CodedInputStream::ConsumedEntireMessage() {
  return legitimate_message_end_;
}

inline bool CodedInputStream::ExpectTag(uint32_t expected) {
  if (expected < (1 << 7)) {
    if (PROTOBUF_PREDICT_TRUE(buffer_ < buffer_end_) &&
        buffer_[0] == expected) {
      Advance(1);
      return true;
    } else {
      return false;
    }
  } else if (expected < (1 << 14)) {
    if (PROTOBUF_PREDICT_TRUE(BufferSize() >= 2) &&
        buffer_[0] == static_cast<uint8_t>(expected | 0x80) &&
        buffer_[1] == static_cast<uint8_t>(expected >> 7)) {
      Advance(2);
      return true;
    } else {
      return false;
    }
  } else {
    // Don't bother optimizing for larger values.
    return false;
  }
}

inline const uint8_t* CodedInputStream::ExpectTagFromArray(
    const uint8_t* buffer, uint32_t expected) {
  if (expected < (1 << 7)) {
    if (buffer[0] == expected) {
      return buffer + 1;
    }
  } else if (expected < (1 << 14)) {
    if (buffer[0] == static_cast<uint8_t>(expected | 0x80) &&
        buffer[1] == static_cast<uint8_t>(expected >> 7)) {
      return buffer + 2;
    }
  }
  return nullptr;
}

inline void CodedInputStream::GetDirectBufferPointerInline(const void** data,
                                                           int* size) {
  *data = buffer_;
  *size = static_cast<int>(buffer_end_ - buffer_);
}

inline bool CodedInputStream::ExpectAtEnd() {
  // If we are at a limit we know no more bytes can be read.  Otherwise, it's
  // hard to say without calling Refresh(), and we'd rather not do that.

  if (buffer_ == buffer_end_ && ((buffer_size_after_limit_ != 0) ||
                                 (total_bytes_read_ == current_limit_))) {
    last_tag_ = 0;                   // Pretend we called ReadTag()...
    legitimate_message_end_ = true;  // ... and it hit EOF.
    return true;
  } else {
    return false;
  }
}

inline int CodedInputStream::CurrentPosition() const {
  return total_bytes_read_ - (BufferSize() + buffer_size_after_limit_);
}

inline void CodedInputStream::Advance(int amount) { buffer_ += amount; }

inline void CodedInputStream::SetRecursionLimit(int limit) {
  recursion_budget_ += limit - recursion_limit_;
  recursion_limit_ = limit;
}

inline bool CodedInputStream::IncrementRecursionDepth() {
  --recursion_budget_;
  return recursion_budget_ >= 0;
}

inline void CodedInputStream::DecrementRecursionDepth() {
  if (recursion_budget_ < recursion_limit_) ++recursion_budget_;
}

inline void CodedInputStream::UnsafeDecrementRecursionDepth() {
  assert(recursion_budget_ < recursion_limit_);
  ++recursion_budget_;
}

inline void CodedInputStream::SetExtensionRegistry(const DescriptorPool* pool,
                                                   MessageFactory* factory) {
  extension_pool_ = pool;
  extension_factory_ = factory;
}

inline const DescriptorPool* CodedInputStream::GetExtensionPool() {
  return extension_pool_;
}

inline MessageFactory* CodedInputStream::GetExtensionFactory() {
  return extension_factory_;
}

inline int CodedInputStream::BufferSize() const {
  return static_cast<int>(buffer_end_ - buffer_);
}

inline CodedInputStream::CodedInputStream(ZeroCopyInputStream* input)
    : buffer_(nullptr),
      buffer_end_(nullptr),
      input_(input),
      total_bytes_read_(0),
      overflow_bytes_(0),
      last_tag_(0),
      legitimate_message_end_(false),
      aliasing_enabled_(false),
      current_limit_(std::numeric_limits<int32_t>::max()),
      buffer_size_after_limit_(0),
      total_bytes_limit_(kDefaultTotalBytesLimit),
      recursion_budget_(default_recursion_limit_),
      recursion_limit_(default_recursion_limit_),
      extension_pool_(nullptr),
      extension_factory_(nullptr) {
  // Eagerly Refresh() so buffer space is immediately available.
  Refresh();
}

inline CodedInputStream::CodedInputStream(const uint8_t* buffer, int size)
    : buffer_(buffer),
      buffer_end_(buffer + size),
      input_(nullptr),
      total_bytes_read_(size),
      overflow_bytes_(0),
      last_tag_(0),
      legitimate_message_end_(false),
      aliasing_enabled_(false),
      current_limit_(size),
      buffer_size_after_limit_(0),
      total_bytes_limit_(kDefaultTotalBytesLimit),
      recursion_budget_(default_recursion_limit_),
      recursion_limit_(default_recursion_limit_),
      extension_pool_(nullptr),
      extension_factory_(nullptr) {
  // Note that setting current_limit_ == size is important to prevent some
  // code paths from trying to access input_ and segfaulting.
}

inline bool CodedInputStream::IsFlat() const { return input_ == nullptr; }

inline bool CodedInputStream::Skip(int count) {
  if (count < 0) return false;  // security: count is often user-supplied

  const int original_buffer_size = BufferSize();

  if (count <= original_buffer_size) {
    // Just skipping within the current buffer.  Easy.
    Advance(count);
    return true;
  }

  return SkipFallback(count, original_buffer_size);
}

template <class Stream, class>
inline CodedOutputStream::CodedOutputStream(Stream* stream)
    : impl_(stream, IsDefaultSerializationDeterministic(), &cur_),
      start_count_(stream->ByteCount()) {
  InitEagerly(stream);
}

template <class Stream, class>
inline CodedOutputStream::CodedOutputStream(Stream* stream, bool eager_init)
    : impl_(stream, IsDefaultSerializationDeterministic(), &cur_),
      start_count_(stream->ByteCount()) {
  if (eager_init) {
    InitEagerly(stream);
  }
}

template <class Stream>
inline void CodedOutputStream::InitEagerly(Stream* stream) {
  void* data;
  int size;
  if (PROTOBUF_PREDICT_TRUE(stream->Next(&data, &size) && size > 0)) {
    cur_ = impl_.SetInitialBuffer(data, size);
  }
}

inline uint8_t* CodedOutputStream::WriteVarint32ToArray(uint32_t value,
                                                        uint8_t* target) {
  return EpsCopyOutputStream::UnsafeVarint(value, target);
}

inline uint8_t* CodedOutputStream::WriteVarint32ToArrayOutOfLine(
    uint32_t value, uint8_t* target) {
  target[0] = static_cast<uint8_t>(value);
  if (value < 0x80) {
    return target + 1;
  } else {
    return WriteVarint32ToArrayOutOfLineHelper(value, target);
  }
}

inline uint8_t* CodedOutputStream::WriteVarint64ToArray(uint64_t value,
                                                        uint8_t* target) {
  return EpsCopyOutputStream::UnsafeVarint(value, target);
}

inline void CodedOutputStream::WriteVarint32SignExtended(int32_t value) {
  WriteVarint64(static_cast<uint64_t>(value));
}

inline uint8_t* CodedOutputStream::WriteVarint32SignExtendedToArray(
    int32_t value, uint8_t* target) {
  return WriteVarint64ToArray(static_cast<uint64_t>(value), target);
}

inline uint8_t* CodedOutputStream::WriteLittleEndian32ToArray(uint32_t value,
                                                              uint8_t* target) {
#if defined(PROTOBUF_LITTLE_ENDIAN) && \
    !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
  memcpy(target, &value, sizeof(value));
#else
  target[0] = static_cast<uint8_t>(value);
  target[1] = static_cast<uint8_t>(value >> 8);
  target[2] = static_cast<uint8_t>(value >> 16);
  target[3] = static_cast<uint8_t>(value >> 24);
#endif
  return target + sizeof(value);
}

inline uint8_t* CodedOutputStream::WriteLittleEndian64ToArray(uint64_t value,
                                                              uint8_t* target) {
#if defined(PROTOBUF_LITTLE_ENDIAN) && \
    !defined(PROTOBUF_DISABLE_LITTLE_ENDIAN_OPT_FOR_TEST)
  memcpy(target, &value, sizeof(value));
#else
  uint32_t part0 = static_cast<uint32_t>(value);
  uint32_t part1 = static_cast<uint32_t>(value >> 32);

  target[0] = static_cast<uint8_t>(part0);
  target[1] = static_cast<uint8_t>(part0 >> 8);
  target[2] = static_cast<uint8_t>(part0 >> 16);
  target[3] = static_cast<uint8_t>(part0 >> 24);
  target[4] = static_cast<uint8_t>(part1);
  target[5] = static_cast<uint8_t>(part1 >> 8);
  target[6] = static_cast<uint8_t>(part1 >> 16);
  target[7] = static_cast<uint8_t>(part1 >> 24);
#endif
  return target + sizeof(value);
}

inline void CodedOutputStream::WriteVarint32(uint32_t value) {
  cur_ = impl_.EnsureSpace(cur_);
  SetCur(WriteVarint32ToArray(value, Cur()));
}

inline void CodedOutputStream::WriteVarint64(uint64_t value) {
  cur_ = impl_.EnsureSpace(cur_);
  SetCur(WriteVarint64ToArray(value, Cur()));
}

inline void CodedOutputStream::WriteTag(uint32_t value) {
  WriteVarint32(value);
}

inline uint8_t* CodedOutputStream::WriteTagToArray(uint32_t value,
                                                   uint8_t* target) {
  return WriteVarint32ToArray(value, target);
}

inline size_t CodedOutputStream::VarintSize32(uint32_t value) {
  // This computes value == 0 ? 1 : floor(log2(value)) / 7 + 1
  // Use an explicit multiplication to implement the divide of
  // a number in the 1..31 range.
  // Explicit OR 0x1 to avoid calling Bits::Log2FloorNonZero(0), which is
  // undefined.
  uint32_t log2value = Bits::Log2FloorNonZero(value | 0x1);
  return static_cast<size_t>((log2value * 9 + 73) / 64);
}

inline size_t CodedOutputStream::VarintSize32PlusOne(uint32_t value) {
  // Same as above, but one more.
  uint32_t log2value = Bits::Log2FloorNonZero(value | 0x1);
  return static_cast<size_t>((log2value * 9 + 73 + 64) / 64);
}

inline size_t CodedOutputStream::VarintSize64(uint64_t value) {
  // This computes value == 0 ? 1 : floor(log2(value)) / 7 + 1
  // Use an explicit multiplication to implement the divide of
  // a number in the 1..63 range.
  // Explicit OR 0x1 to avoid calling Bits::Log2FloorNonZero(0), which is
  // undefined.
  uint32_t log2value = Bits::Log2FloorNonZero64(value | 0x1);
  return static_cast<size_t>((log2value * 9 + 73) / 64);
}

inline size_t CodedOutputStream::VarintSize64PlusOne(uint64_t value) {
  // Same as above, but one more.
  uint32_t log2value = Bits::Log2FloorNonZero64(value | 0x1);
  return static_cast<size_t>((log2value * 9 + 73 + 64) / 64);
}

inline size_t CodedOutputStream::VarintSize32SignExtended(int32_t value) {
  return VarintSize64(static_cast<uint64_t>(int64_t{value}));
}

inline size_t CodedOutputStream::VarintSize32SignExtendedPlusOne(
    int32_t value) {
  return VarintSize64PlusOne(static_cast<uint64_t>(int64_t{value}));
}

inline void CodedOutputStream::WriteString(const std::string& str) {
  WriteRaw(str.data(), static_cast<int>(str.size()));
}

inline void CodedOutputStream::WriteRawMaybeAliased(const void* data,
                                                    int size) {
  cur_ = impl_.WriteRawMaybeAliased(data, size, cur_);
}

inline uint8_t* CodedOutputStream::WriteRawToArray(const void* data, int size,
                                                   uint8_t* target) {
  memcpy(target, data, size);
  return target + size;
}

inline uint8_t* CodedOutputStream::WriteStringToArray(const std::string& str,
                                                      uint8_t* target) {
  return WriteRawToArray(str.data(), static_cast<int>(str.size()), target);
}

}  // namespace io
}  // namespace protobuf
}  // namespace google

#if defined(_MSC_VER) && _MSC_VER >= 1300 && !defined(__INTEL_COMPILER)
#pragma runtime_checks("c", restore)
#endif  // _MSC_VER && !defined(__INTEL_COMPILER)

#include <google/protobuf/port_undef.inc>

#endif  // GOOGLE_PROTOBUF_IO_CODED_STREAM_H__
