diff --git a/src/google/protobuf/struct.pb.cc b/src/google/protobuf/struct.pb.cc
index e020597..8f2d484 100644
--- a/src/google/protobuf/struct.pb.cc
+++ b/src/google/protobuf/struct.pb.cc
@@ -1,198 +1,209 @@
 // Generated by the protocol buffer compiler.  DO NOT EDIT!
 // source: google/protobuf/struct.proto
 
-#define INTERNAL_SUPPRESS_PROTOBUF_FIELD_DEPRECATION
 #include <google/protobuf/struct.pb.h>
 
 #include <algorithm>
 
 #include <google/protobuf/stubs/common.h>
 #include <google/protobuf/stubs/port.h>
-#include <google/protobuf/stubs/once.h>
 #include <google/protobuf/io/coded_stream.h>
 #include <google/protobuf/wire_format_lite_inl.h>
 #include <google/protobuf/descriptor.h>
 #include <google/protobuf/generated_message_reflection.h>
 #include <google/protobuf/reflection_ops.h>
 #include <google/protobuf/wire_format.h>
+// This is a temporary google only hack
+#ifdef GOOGLE_PROTOBUF_ENFORCE_UNIQUENESS
+#include "third_party/protobuf/version.h"
+#endif
 // @@protoc_insertion_point(includes)
 
+namespace protobuf_google_2fprotobuf_2fstruct_2eproto {
+extern PROTOBUF_INTERNAL_EXPORT_protobuf_google_2fprotobuf_2fstruct_2eproto ::google::protobuf::internal::SCCInfo<0> scc_info_ListValue;
+}  // namespace protobuf_google_2fprotobuf_2fstruct_2eproto
 namespace google {
 namespace protobuf {
-
-namespace {
-
-const ::google::protobuf::Descriptor* Struct_descriptor_ = NULL;
-const ::google::protobuf::internal::GeneratedMessageReflection*
-  Struct_reflection_ = NULL;
-const ::google::protobuf::Descriptor* Struct_FieldsEntry_descriptor_ = NULL;
-const ::google::protobuf::Descriptor* Value_descriptor_ = NULL;
-const ::google::protobuf::internal::GeneratedMessageReflection*
-  Value_reflection_ = NULL;
-struct ValueOneofInstance {
+class Struct_FieldsEntry_DoNotUseDefaultTypeInternal {
+ public:
+  ::google::protobuf::internal::ExplicitlyConstructed<Struct_FieldsEntry_DoNotUse>
+      _instance;
+} _Struct_FieldsEntry_DoNotUse_default_instance_;
+class StructDefaultTypeInternal {
+ public:
+  ::google::protobuf::internal::ExplicitlyConstructed<Struct>
+      _instance;
+} _Struct_default_instance_;
+class ValueDefaultTypeInternal {
+ public:
+  ::google::protobuf::internal::ExplicitlyConstructed<Value>
+      _instance;
   int null_value_;
   double number_value_;
   ::google::protobuf::internal::ArenaStringPtr string_value_;
   bool bool_value_;
   const ::google::protobuf::Struct* struct_value_;
   const ::google::protobuf::ListValue* list_value_;
-}* Value_default_oneof_instance_ = NULL;
-const ::google::protobuf::Descriptor* ListValue_descriptor_ = NULL;
-const ::google::protobuf::internal::GeneratedMessageReflection*
-  ListValue_reflection_ = NULL;
-const ::google::protobuf::EnumDescriptor* NullValue_descriptor_ = NULL;
-
-}  // namespace
-
-
-void protobuf_AssignDesc_google_2fprotobuf_2fstruct_2eproto() {
-  protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
-  const ::google::protobuf::FileDescriptor* file =
-    ::google::protobuf::DescriptorPool::generated_pool()->FindFileByName(
-      "google/protobuf/struct.proto");
-  GOOGLE_CHECK(file != NULL);
-  Struct_descriptor_ = file->message_type(0);
-  static const int Struct_offsets_[1] = {
-    GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Struct, fields_),
-  };
-  Struct_reflection_ =
-    ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
-      Struct_descriptor_,
-      Struct::default_instance_,
-      Struct_offsets_,
-      -1,
-      -1,
-      -1,
-      sizeof(Struct),
-      GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Struct, _internal_metadata_),
-      GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Struct, _is_default_instance_));
-  Struct_FieldsEntry_descriptor_ = Struct_descriptor_->nested_type(0);
-  Value_descriptor_ = file->message_type(1);
-  static const int Value_offsets_[7] = {
-    PROTO2_GENERATED_DEFAULT_ONEOF_FIELD_OFFSET(Value_default_oneof_instance_, null_value_),
-    PROTO2_GENERATED_DEFAULT_ONEOF_FIELD_OFFSET(Value_default_oneof_instance_, number_value_),
-    PROTO2_GENERATED_DEFAULT_ONEOF_FIELD_OFFSET(Value_default_oneof_instance_, string_value_),
-    PROTO2_GENERATED_DEFAULT_ONEOF_FIELD_OFFSET(Value_default_oneof_instance_, bool_value_),
-    PROTO2_GENERATED_DEFAULT_ONEOF_FIELD_OFFSET(Value_default_oneof_instance_, struct_value_),
-    PROTO2_GENERATED_DEFAULT_ONEOF_FIELD_OFFSET(Value_default_oneof_instance_, list_value_),
-    GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Value, kind_),
-  };
-  Value_reflection_ =
-    ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
-      Value_descriptor_,
-      Value::default_instance_,
-      Value_offsets_,
-      -1,
-      -1,
-      -1,
-      Value_default_oneof_instance_,
-      GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Value, _oneof_case_[0]),
-      sizeof(Value),
-      GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Value, _internal_metadata_),
-      GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(Value, _is_default_instance_));
-  ListValue_descriptor_ = file->message_type(2);
-  static const int ListValue_offsets_[1] = {
-    GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ListValue, values_),
-  };
-  ListValue_reflection_ =
-    ::google::protobuf::internal::GeneratedMessageReflection::NewGeneratedMessageReflection(
-      ListValue_descriptor_,
-      ListValue::default_instance_,
-      ListValue_offsets_,
-      -1,
-      -1,
-      -1,
-      sizeof(ListValue),
-      GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ListValue, _internal_metadata_),
-      GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(ListValue, _is_default_instance_));
-  NullValue_descriptor_ = file->enum_type(0);
-}
-
-namespace {
-
-GOOGLE_PROTOBUF_DECLARE_ONCE(protobuf_AssignDescriptors_once_);
-inline void protobuf_AssignDescriptorsOnce() {
-  ::google::protobuf::GoogleOnceInit(&protobuf_AssignDescriptors_once_,
-                 &protobuf_AssignDesc_google_2fprotobuf_2fstruct_2eproto);
-}
-
-void protobuf_RegisterTypes(const ::std::string&) {
-  protobuf_AssignDescriptorsOnce();
-  ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
-      Struct_descriptor_, &Struct::default_instance());
-  ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
-        Struct_FieldsEntry_descriptor_,
-        ::google::protobuf::internal::MapEntry<
-            ::std::string,
-            ::google::protobuf::Value,
-            ::google::protobuf::internal::WireFormatLite::TYPE_STRING,
-            ::google::protobuf::internal::WireFormatLite::TYPE_MESSAGE,
-            0>::CreateDefaultInstance(
-                Struct_FieldsEntry_descriptor_));
-  ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
-      Value_descriptor_, &Value::default_instance());
-  ::google::protobuf::MessageFactory::InternalRegisterGeneratedMessage(
-      ListValue_descriptor_, &ListValue::default_instance());
-}
-
-}  // namespace
-
-void protobuf_ShutdownFile_google_2fprotobuf_2fstruct_2eproto() {
-  delete Struct::default_instance_;
-  delete Struct_reflection_;
-  delete Value::default_instance_;
-  delete Value_default_oneof_instance_;
-  delete Value_reflection_;
-  delete ListValue::default_instance_;
-  delete ListValue_reflection_;
-}
-
-void protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto() {
-  static bool already_here = false;
-  if (already_here) return;
-  already_here = true;
+} _Value_default_instance_;
+class ListValueDefaultTypeInternal {
+ public:
+  ::google::protobuf::internal::ExplicitlyConstructed<ListValue>
+      _instance;
+} _ListValue_default_instance_;
+}  // namespace protobuf
+}  // namespace google
+namespace protobuf_google_2fprotobuf_2fstruct_2eproto {
+static void InitDefaultsListValue() {
   GOOGLE_PROTOBUF_VERIFY_VERSION;
 
-  ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
-    "\n\034google/protobuf/struct.proto\022\017google.p"
-    "rotobuf\"\204\001\n\006Struct\0223\n\006fields\030\001 \003(\0132#.goo"
-    "gle.protobuf.Struct.FieldsEntry\032E\n\013Field"
-    "sEntry\022\013\n\003key\030\001 \001(\t\022%\n\005value\030\002 \001(\0132\026.goo"
-    "gle.protobuf.Value:\0028\001\"\352\001\n\005Value\0220\n\nnull"
-    "_value\030\001 \001(\0162\032.google.protobuf.NullValue"
-    "H\000\022\026\n\014number_value\030\002 \001(\001H\000\022\026\n\014string_val"
-    "ue\030\003 \001(\tH\000\022\024\n\nbool_value\030\004 \001(\010H\000\022/\n\014stru"
-    "ct_value\030\005 \001(\0132\027.google.protobuf.StructH"
-    "\000\0220\n\nlist_value\030\006 \001(\0132\032.google.protobuf."
-    "ListValueH\000B\006\n\004kind\"3\n\tListValue\022&\n\006valu"
-    "es\030\001 \003(\0132\026.google.protobuf.Value*\033\n\tNull"
-    "Value\022\016\n\nNULL_VALUE\020\000BN\n\023com.google.prot"
-    "obufB\013StructProtoP\001\240\001\001\242\002\003GPB\252\002\036Google.Pr"
-    "otobuf.WellKnownTypesb\006proto3", 589);
-  ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
-    "google/protobuf/struct.proto", &protobuf_RegisterTypes);
-  Struct::default_instance_ = new Struct();
-  Value::default_instance_ = new Value();
-  Value_default_oneof_instance_ = new ValueOneofInstance();
-  ListValue::default_instance_ = new ListValue();
-  Struct::default_instance_->InitAsDefaultInstance();
-  Value::default_instance_->InitAsDefaultInstance();
-  ListValue::default_instance_->InitAsDefaultInstance();
-  ::google::protobuf::internal::OnShutdown(&protobuf_ShutdownFile_google_2fprotobuf_2fstruct_2eproto);
+  {
+    void* ptr = &::google::protobuf::_Struct_FieldsEntry_DoNotUse_default_instance_;
+    new (ptr) ::google::protobuf::Struct_FieldsEntry_DoNotUse();
+  }
+  {
+    void* ptr = &::google::protobuf::_Struct_default_instance_;
+    new (ptr) ::google::protobuf::Struct();
+    ::google::protobuf::internal::OnShutdownDestroyMessage(ptr);
+  }
+  {
+    void* ptr = &::google::protobuf::_Value_default_instance_;
+    new (ptr) ::google::protobuf::Value();
+    ::google::protobuf::internal::OnShutdownDestroyMessage(ptr);
+  }
+  {
+    void* ptr = &::google::protobuf::_ListValue_default_instance_;
+    new (ptr) ::google::protobuf::ListValue();
+    ::google::protobuf::internal::OnShutdownDestroyMessage(ptr);
+  }
+  ::google::protobuf::Struct_FieldsEntry_DoNotUse::InitAsDefaultInstance();
+  ::google::protobuf::Struct::InitAsDefaultInstance();
+  ::google::protobuf::Value::InitAsDefaultInstance();
+  ::google::protobuf::ListValue::InitAsDefaultInstance();
 }
 
-// Force AddDescriptors() to be called at static initialization time.
-struct StaticDescriptorInitializer_google_2fprotobuf_2fstruct_2eproto {
-  StaticDescriptorInitializer_google_2fprotobuf_2fstruct_2eproto() {
-    protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
-  }
-} static_descriptor_initializer_google_2fprotobuf_2fstruct_2eproto_;
-const ::google::protobuf::EnumDescriptor* NullValue_descriptor() {
+LIBPROTOBUF_EXPORT ::google::protobuf::internal::SCCInfo<0> scc_info_ListValue =
+    {{ATOMIC_VAR_INIT(::google::protobuf::internal::SCCInfoBase::kUninitialized), 0, InitDefaultsListValue}, {}};
+
+void InitDefaults() {
+  ::google::protobuf::internal::InitSCC(&scc_info_ListValue.base);
+}
+
+::google::protobuf::Metadata file_level_metadata[4];
+const ::google::protobuf::EnumDescriptor* file_level_enum_descriptors[1];
+
+const ::google::protobuf::uint32 TableStruct::offsets[] GOOGLE_PROTOBUF_ATTRIBUTE_SECTION_VARIABLE(protodesc_cold) = {
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::Struct_FieldsEntry_DoNotUse, _has_bits_),
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::Struct_FieldsEntry_DoNotUse, _internal_metadata_),
+  ~0u,  // no _extensions_
+  ~0u,  // no _oneof_case_
+  ~0u,  // no _weak_field_map_
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::Struct_FieldsEntry_DoNotUse, key_),
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::Struct_FieldsEntry_DoNotUse, value_),
+  0,
+  1,
+  ~0u,  // no _has_bits_
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::Struct, _internal_metadata_),
+  ~0u,  // no _extensions_
+  ~0u,  // no _oneof_case_
+  ~0u,  // no _weak_field_map_
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::Struct, fields_),
+  ~0u,  // no _has_bits_
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::Value, _internal_metadata_),
+  ~0u,  // no _extensions_
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::Value, _oneof_case_[0]),
+  ~0u,  // no _weak_field_map_
+  offsetof(::google::protobuf::ValueDefaultTypeInternal, null_value_),
+  offsetof(::google::protobuf::ValueDefaultTypeInternal, number_value_),
+  offsetof(::google::protobuf::ValueDefaultTypeInternal, string_value_),
+  offsetof(::google::protobuf::ValueDefaultTypeInternal, bool_value_),
+  offsetof(::google::protobuf::ValueDefaultTypeInternal, struct_value_),
+  offsetof(::google::protobuf::ValueDefaultTypeInternal, list_value_),
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::Value, kind_),
+  ~0u,  // no _has_bits_
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::ListValue, _internal_metadata_),
+  ~0u,  // no _extensions_
+  ~0u,  // no _oneof_case_
+  ~0u,  // no _weak_field_map_
+  GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::google::protobuf::ListValue, values_),
+};
+static const ::google::protobuf::internal::MigrationSchema schemas[] GOOGLE_PROTOBUF_ATTRIBUTE_SECTION_VARIABLE(protodesc_cold) = {
+  { 0, 7, sizeof(::google::protobuf::Struct_FieldsEntry_DoNotUse)},
+  { 9, -1, sizeof(::google::protobuf::Struct)},
+  { 15, -1, sizeof(::google::protobuf::Value)},
+  { 27, -1, sizeof(::google::protobuf::ListValue)},
+};
+
+static ::google::protobuf::Message const * const file_default_instances[] = {
+  reinterpret_cast<const ::google::protobuf::Message*>(&::google::protobuf::_Struct_FieldsEntry_DoNotUse_default_instance_),
+  reinterpret_cast<const ::google::protobuf::Message*>(&::google::protobuf::_Struct_default_instance_),
+  reinterpret_cast<const ::google::protobuf::Message*>(&::google::protobuf::_Value_default_instance_),
+  reinterpret_cast<const ::google::protobuf::Message*>(&::google::protobuf::_ListValue_default_instance_),
+};
+
+void protobuf_AssignDescriptors() {
+  AddDescriptors();
+  AssignDescriptors(
+      "google/protobuf/struct.proto", schemas, file_default_instances, TableStruct::offsets,
+      file_level_metadata, file_level_enum_descriptors, NULL);
+}
+
+void protobuf_AssignDescriptorsOnce() {
+  static ::google::protobuf::internal::once_flag once;
+  ::google::protobuf::internal::call_once(once, protobuf_AssignDescriptors);
+}
+
+void protobuf_RegisterTypes(const ::std::string&) GOOGLE_PROTOBUF_ATTRIBUTE_COLD;
+void protobuf_RegisterTypes(const ::std::string&) {
   protobuf_AssignDescriptorsOnce();
-  return NullValue_descriptor_;
+  ::google::protobuf::internal::RegisterAllTypes(file_level_metadata, 4);
+}
+
+void AddDescriptorsImpl() {
+  InitDefaults();
+  static const char descriptor[] GOOGLE_PROTOBUF_ATTRIBUTE_SECTION_VARIABLE(protodesc_cold) = {
+      "\n\034google/protobuf/struct.proto\022\017google.p"
+      "rotobuf\"\204\001\n\006Struct\0223\n\006fields\030\001 \003(\0132#.goo"
+      "gle.protobuf.Struct.FieldsEntry\032E\n\013Field"
+      "sEntry\022\013\n\003key\030\001 \001(\t\022%\n\005value\030\002 \001(\0132\026.goo"
+      "gle.protobuf.Value:\0028\001\"\352\001\n\005Value\0220\n\nnull"
+      "_value\030\001 \001(\0162\032.google.protobuf.NullValue"
+      "H\000\022\026\n\014number_value\030\002 \001(\001H\000\022\026\n\014string_val"
+      "ue\030\003 \001(\tH\000\022\024\n\nbool_value\030\004 \001(\010H\000\022/\n\014stru"
+      "ct_value\030\005 \001(\0132\027.google.protobuf.StructH"
+      "\000\0220\n\nlist_value\030\006 \001(\0132\032.google.protobuf."
+      "ListValueH\000B\006\n\004kind\"3\n\tListValue\022&\n\006valu"
+      "es\030\001 \003(\0132\026.google.protobuf.Value*\033\n\tNull"
+      "Value\022\016\n\nNULL_VALUE\020\000B\201\001\n\023com.google.pro"
+      "tobufB\013StructProtoP\001Z1github.com/golang/"
+      "protobuf/ptypes/struct;structpb\370\001\001\242\002\003GPB"
+      "\252\002\036Google.Protobuf.WellKnownTypesb\006proto"
+      "3"
+  };
+  ::google::protobuf::DescriptorPool::InternalAddGeneratedFile(
+      descriptor, 641);
+  ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile(
+    "google/protobuf/struct.proto", &protobuf_RegisterTypes);
+}
+
+void AddDescriptors() {
+  static ::google::protobuf::internal::once_flag once;
+  ::google::protobuf::internal::call_once(once, AddDescriptorsImpl);
+}
+// Force AddDescriptors() to be called at dynamic initialization time.
+struct StaticDescriptorInitializer {
+  StaticDescriptorInitializer() {
+    AddDescriptors();
+  }
+} static_descriptor_initializer;
+}  // namespace protobuf_google_2fprotobuf_2fstruct_2eproto
+namespace google {
+namespace protobuf {
+const ::google::protobuf::EnumDescriptor* NullValue_descriptor() {
+  protobuf_google_2fprotobuf_2fstruct_2eproto::protobuf_AssignDescriptorsOnce();
+  return protobuf_google_2fprotobuf_2fstruct_2eproto::file_level_enum_descriptors[0];
 }
 bool NullValue_IsValid(int value) {
-  switch(value) {
+  switch (value) {
     case 0:
       return true;
     default:
@@ -201,47 +212,56 @@
 }
 
 
-namespace {
+// ===================================================================
 
-static void MergeFromFail(int line) GOOGLE_ATTRIBUTE_COLD;
-static void MergeFromFail(int line) {
-  GOOGLE_CHECK(false) << __FILE__ << ":" << line;
+Struct_FieldsEntry_DoNotUse::Struct_FieldsEntry_DoNotUse() {}
+Struct_FieldsEntry_DoNotUse::Struct_FieldsEntry_DoNotUse(::google::protobuf::Arena* arena) : SuperType(arena) {}
+void Struct_FieldsEntry_DoNotUse::MergeFrom(const Struct_FieldsEntry_DoNotUse& other) {
+  MergeFromInternal(other);
 }
-
-}  // namespace
+::google::protobuf::Metadata Struct_FieldsEntry_DoNotUse::GetMetadata() const {
+  ::protobuf_google_2fprotobuf_2fstruct_2eproto::protobuf_AssignDescriptorsOnce();
+  return ::protobuf_google_2fprotobuf_2fstruct_2eproto::file_level_metadata[0];
+}
+void Struct_FieldsEntry_DoNotUse::MergeFrom(
+    const ::google::protobuf::Message& other) {
+  ::google::protobuf::Message::MergeFrom(other);
+}
 
 
 // ===================================================================
 
+void Struct::InitAsDefaultInstance() {
+}
 #if !defined(_MSC_VER) || _MSC_VER >= 1900
 const int Struct::kFieldsFieldNumber;
 #endif  // !defined(_MSC_VER) || _MSC_VER >= 1900
 
 Struct::Struct()
   : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+  ::google::protobuf::internal::InitSCC(
+      &protobuf_google_2fprotobuf_2fstruct_2eproto::scc_info_ListValue.base);
   SharedCtor();
   // @@protoc_insertion_point(constructor:google.protobuf.Struct)
 }
-
-void Struct::InitAsDefaultInstance() {
-  _is_default_instance_ = true;
+Struct::Struct(::google::protobuf::Arena* arena)
+  : ::google::protobuf::Message(),
+  _internal_metadata_(arena),
+  fields_(arena) {
+  ::google::protobuf::internal::InitSCC(&protobuf_google_2fprotobuf_2fstruct_2eproto::scc_info_ListValue.base);
+  SharedCtor();
+  RegisterArenaDtor(arena);
+  // @@protoc_insertion_point(arena_constructor:google.protobuf.Struct)
 }
-
 Struct::Struct(const Struct& from)
   : ::google::protobuf::Message(),
-    _internal_metadata_(NULL) {
-  SharedCtor();
-  MergeFrom(from);
+      _internal_metadata_(NULL) {
+  _internal_metadata_.MergeFrom(from._internal_metadata_);
+  fields_.MergeFrom(from.fields_);
   // @@protoc_insertion_point(copy_constructor:google.protobuf.Struct)
 }
 
 void Struct::SharedCtor() {
-    _is_default_instance_ = false;
-  _cached_size_ = 0;
-  fields_.SetAssignDescriptorCallback(
-      protobuf_AssignDescriptorsOnce);
-  fields_.SetEntryDescriptor(
-      &::google::protobuf::Struct_FieldsEntry_descriptor_);
 }
 
 Struct::~Struct() {
@@ -250,79 +270,79 @@
 }
 
 void Struct::SharedDtor() {
-  if (this != default_instance_) {
-  }
+  GOOGLE_DCHECK(GetArenaNoVirtual() == NULL);
 }
 
+void Struct::ArenaDtor(void* object) {
+  Struct* _this = reinterpret_cast< Struct* >(object);
+  (void)_this;
+}
+void Struct::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
 void Struct::SetCachedSize(int size) const {
-  GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
-  _cached_size_ = size;
-  GOOGLE_SAFE_CONCURRENT_WRITES_END();
+  _cached_size_.Set(size);
 }
 const ::google::protobuf::Descriptor* Struct::descriptor() {
-  protobuf_AssignDescriptorsOnce();
-  return Struct_descriptor_;
+  ::protobuf_google_2fprotobuf_2fstruct_2eproto::protobuf_AssignDescriptorsOnce();
+  return ::protobuf_google_2fprotobuf_2fstruct_2eproto::file_level_metadata[kIndexInFileMessages].descriptor;
 }
 
 const Struct& Struct::default_instance() {
-  if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
-  return *default_instance_;
+  ::google::protobuf::internal::InitSCC(&protobuf_google_2fprotobuf_2fstruct_2eproto::scc_info_ListValue.base);
+  return *internal_default_instance();
 }
 
-Struct* Struct::default_instance_ = NULL;
-
-Struct* Struct::New(::google::protobuf::Arena* arena) const {
-  Struct* n = new Struct;
-  if (arena != NULL) {
-    arena->Own(n);
-  }
-  return n;
-}
 
 void Struct::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Struct)
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  // Prevent compiler warnings about cached_has_bits being unused
+  (void) cached_has_bits;
+
   fields_.Clear();
+  _internal_metadata_.Clear();
 }
 
 bool Struct::MergePartialFromCodedStream(
     ::google::protobuf::io::CodedInputStream* input) {
-#define DO_(EXPRESSION) if (!(EXPRESSION)) goto failure
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
   ::google::protobuf::uint32 tag;
   // @@protoc_insertion_point(parse_start:google.protobuf.Struct)
   for (;;) {
-    ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+    ::std::pair<::google::protobuf::uint32, bool> p = input->ReadTagWithCutoffNoLastTag(127u);
     tag = p.first;
     if (!p.second) goto handle_unusual;
     switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
       // map<string, .google.protobuf.Value> fields = 1;
       case 1: {
-        if (tag == 10) {
-          DO_(input->IncrementRecursionDepth());
-         parse_loop_fields:
-          ::google::protobuf::scoped_ptr<Struct_FieldsEntry> entry(fields_.NewEntry());
+        if (static_cast< ::google::protobuf::uint8>(tag) ==
+            static_cast< ::google::protobuf::uint8>(10u /* 10 & 0xFF */)) {
+          Struct_FieldsEntry_DoNotUse::Parser< ::google::protobuf::internal::MapField<
+              Struct_FieldsEntry_DoNotUse,
+              ::std::string, ::google::protobuf::Value,
+              ::google::protobuf::internal::WireFormatLite::TYPE_STRING,
+              ::google::protobuf::internal::WireFormatLite::TYPE_MESSAGE,
+              0 >,
+            ::google::protobuf::Map< ::std::string, ::google::protobuf::Value > > parser(&fields_);
           DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
-              input, entry.get()));
-          (*mutable_fields())[entry->key()].Swap(entry->mutable_value());
+              input, &parser));
           DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
-            entry->key().data(), entry->key().length(),
+            parser.key().data(), static_cast<int>(parser.key().length()),
             ::google::protobuf::internal::WireFormatLite::PARSE,
             "google.protobuf.Struct.FieldsEntry.key"));
         } else {
           goto handle_unusual;
         }
-        if (input->ExpectTag(10)) goto parse_loop_fields;
-        input->UnsafeDecrementRecursionDepth();
-        if (input->ExpectAtEnd()) goto success;
         break;
       }
 
       default: {
       handle_unusual:
-        if (tag == 0 ||
-            ::google::protobuf::internal::WireFormatLite::GetTagWireType(tag) ==
-            ::google::protobuf::internal::WireFormatLite::WIRETYPE_END_GROUP) {
+        if (tag == 0) {
           goto success;
         }
-        DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+        DO_(::google::protobuf::internal::WireFormat::SkipField(
+              input, tag, _internal_metadata_.mutable_unknown_fields()));
         break;
       }
     }
@@ -339,148 +359,296 @@
 void Struct::SerializeWithCachedSizes(
     ::google::protobuf::io::CodedOutputStream* output) const {
   // @@protoc_insertion_point(serialize_start:google.protobuf.Struct)
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  (void) cached_has_bits;
+
   // map<string, .google.protobuf.Value> fields = 1;
-  {
-    ::google::protobuf::scoped_ptr<Struct_FieldsEntry> entry;
-    for (::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::const_iterator
-        it = this->fields().begin();
-        it != this->fields().end(); ++it) {
-      entry.reset(fields_.NewEntryWrapper(it->first, it->second));
-      ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
-          1, *entry, output);
-      ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
-        it->first.data(), it->first.length(),
-        ::google::protobuf::internal::WireFormatLite::SERIALIZE,
-        "google.protobuf.Struct.FieldsEntry.key");
+  if (!this->fields().empty()) {
+    typedef ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::const_pointer
+        ConstPtr;
+    typedef ConstPtr SortItem;
+    typedef ::google::protobuf::internal::CompareByDerefFirst<SortItem> Less;
+    struct Utf8Check {
+      static void Check(ConstPtr p) {
+        ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+          p->first.data(), static_cast<int>(p->first.length()),
+          ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+          "google.protobuf.Struct.FieldsEntry.key");
+      }
+    };
+
+    if (output->IsSerializationDeterministic() &&
+        this->fields().size() > 1) {
+      ::std::unique_ptr<SortItem[]> items(
+          new SortItem[this->fields().size()]);
+      typedef ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::size_type size_type;
+      size_type n = 0;
+      for (::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::const_iterator
+          it = this->fields().begin();
+          it != this->fields().end(); ++it, ++n) {
+        items[static_cast<ptrdiff_t>(n)] = SortItem(&*it);
+      }
+      ::std::sort(&items[0], &items[static_cast<ptrdiff_t>(n)], Less());
+      ::std::unique_ptr<Struct_FieldsEntry_DoNotUse> entry;
+      for (size_type i = 0; i < n; i++) {
+        entry.reset(fields_.NewEntryWrapper(
+            items[static_cast<ptrdiff_t>(i)]->first, items[static_cast<ptrdiff_t>(i)]->second));
+        ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+            1, *entry, output);
+        if (entry->GetArena() != NULL) {
+          entry.release();
+        }
+        Utf8Check::Check(items[static_cast<ptrdiff_t>(i)]);
+      }
+    } else {
+      ::std::unique_ptr<Struct_FieldsEntry_DoNotUse> entry;
+      for (::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::const_iterator
+          it = this->fields().begin();
+          it != this->fields().end(); ++it) {
+        entry.reset(fields_.NewEntryWrapper(
+            it->first, it->second));
+        ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
+            1, *entry, output);
+        if (entry->GetArena() != NULL) {
+          entry.release();
+        }
+        Utf8Check::Check(&*it);
+      }
     }
   }
 
+  if ((_internal_metadata_.have_unknown_fields() &&  ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) {
+    ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+        (::google::protobuf::internal::GetProto3PreserveUnknownsDefault()   ? _internal_metadata_.unknown_fields()   : _internal_metadata_.default_instance()), output);
+  }
   // @@protoc_insertion_point(serialize_end:google.protobuf.Struct)
 }
 
-::google::protobuf::uint8* Struct::SerializeWithCachedSizesToArray(
-    ::google::protobuf::uint8* target) const {
+::google::protobuf::uint8* Struct::InternalSerializeWithCachedSizesToArray(
+    bool deterministic, ::google::protobuf::uint8* target) const {
+  (void)deterministic; // Unused
   // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Struct)
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  (void) cached_has_bits;
+
   // map<string, .google.protobuf.Value> fields = 1;
-  {
-    ::google::protobuf::scoped_ptr<Struct_FieldsEntry> entry;
-    for (::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::const_iterator
-        it = this->fields().begin();
-        it != this->fields().end(); ++it) {
-      entry.reset(fields_.NewEntryWrapper(it->first, it->second));
-      target = ::google::protobuf::internal::WireFormatLite::
-          WriteMessageNoVirtualToArray(
-              1, *entry, target);
-      ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
-        it->first.data(), it->first.length(),
-        ::google::protobuf::internal::WireFormatLite::SERIALIZE,
-        "google.protobuf.Struct.FieldsEntry.key");
+  if (!this->fields().empty()) {
+    typedef ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::const_pointer
+        ConstPtr;
+    typedef ConstPtr SortItem;
+    typedef ::google::protobuf::internal::CompareByDerefFirst<SortItem> Less;
+    struct Utf8Check {
+      static void Check(ConstPtr p) {
+        ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
+          p->first.data(), static_cast<int>(p->first.length()),
+          ::google::protobuf::internal::WireFormatLite::SERIALIZE,
+          "google.protobuf.Struct.FieldsEntry.key");
+      }
+    };
+
+    if (deterministic &&
+        this->fields().size() > 1) {
+      ::std::unique_ptr<SortItem[]> items(
+          new SortItem[this->fields().size()]);
+      typedef ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::size_type size_type;
+      size_type n = 0;
+      for (::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::const_iterator
+          it = this->fields().begin();
+          it != this->fields().end(); ++it, ++n) {
+        items[static_cast<ptrdiff_t>(n)] = SortItem(&*it);
+      }
+      ::std::sort(&items[0], &items[static_cast<ptrdiff_t>(n)], Less());
+      ::std::unique_ptr<Struct_FieldsEntry_DoNotUse> entry;
+      for (size_type i = 0; i < n; i++) {
+        entry.reset(fields_.NewEntryWrapper(
+            items[static_cast<ptrdiff_t>(i)]->first, items[static_cast<ptrdiff_t>(i)]->second));
+        target = ::google::protobuf::internal::WireFormatLite::
+                   InternalWriteMessageNoVirtualToArray(
+                       1, *entry, deterministic, target);
+;
+        if (entry->GetArena() != NULL) {
+          entry.release();
+        }
+        Utf8Check::Check(items[static_cast<ptrdiff_t>(i)]);
+      }
+    } else {
+      ::std::unique_ptr<Struct_FieldsEntry_DoNotUse> entry;
+      for (::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::const_iterator
+          it = this->fields().begin();
+          it != this->fields().end(); ++it) {
+        entry.reset(fields_.NewEntryWrapper(
+            it->first, it->second));
+        target = ::google::protobuf::internal::WireFormatLite::
+                   InternalWriteMessageNoVirtualToArray(
+                       1, *entry, deterministic, target);
+;
+        if (entry->GetArena() != NULL) {
+          entry.release();
+        }
+        Utf8Check::Check(&*it);
+      }
     }
   }
 
+  if ((_internal_metadata_.have_unknown_fields() &&  ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) {
+    target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+        (::google::protobuf::internal::GetProto3PreserveUnknownsDefault()   ? _internal_metadata_.unknown_fields()   : _internal_metadata_.default_instance()), target);
+  }
   // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Struct)
   return target;
 }
 
-int Struct::ByteSize() const {
-  int total_size = 0;
+size_t Struct::ByteSizeLong() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Struct)
+  size_t total_size = 0;
 
+  if ((_internal_metadata_.have_unknown_fields() &&  ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) {
+    total_size +=
+      ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+        (::google::protobuf::internal::GetProto3PreserveUnknownsDefault()   ? _internal_metadata_.unknown_fields()   : _internal_metadata_.default_instance()));
+  }
   // map<string, .google.protobuf.Value> fields = 1;
-  total_size += 1 * this->fields_size();
+  total_size += 1 *
+      ::google::protobuf::internal::FromIntSize(this->fields_size());
   {
-    ::google::protobuf::scoped_ptr<Struct_FieldsEntry> entry;
+    ::std::unique_ptr<Struct_FieldsEntry_DoNotUse> entry;
     for (::google::protobuf::Map< ::std::string, ::google::protobuf::Value >::const_iterator
         it = this->fields().begin();
         it != this->fields().end(); ++it) {
+      if (entry.get() != NULL && entry->GetArena() != NULL) {
+        entry.release();
+      }
       entry.reset(fields_.NewEntryWrapper(it->first, it->second));
       total_size += ::google::protobuf::internal::WireFormatLite::
           MessageSizeNoVirtual(*entry);
     }
+    if (entry.get() != NULL && entry->GetArena() != NULL) {
+      entry.release();
+    }
   }
 
-  GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
-  _cached_size_ = total_size;
-  GOOGLE_SAFE_CONCURRENT_WRITES_END();
+  int cached_size = ::google::protobuf::internal::ToCachedSize(total_size);
+  SetCachedSize(cached_size);
   return total_size;
 }
 
 void Struct::MergeFrom(const ::google::protobuf::Message& from) {
-  if (GOOGLE_PREDICT_FALSE(&from == this)) MergeFromFail(__LINE__);
-  const Struct* source = 
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Struct)
+  GOOGLE_DCHECK_NE(&from, this);
+  const Struct* source =
       ::google::protobuf::internal::DynamicCastToGenerated<const Struct>(
           &from);
   if (source == NULL) {
+  // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Struct)
     ::google::protobuf::internal::ReflectionOps::Merge(from, this);
   } else {
+  // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Struct)
     MergeFrom(*source);
   }
 }
 
 void Struct::MergeFrom(const Struct& from) {
-  if (GOOGLE_PREDICT_FALSE(&from == this)) MergeFromFail(__LINE__);
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Struct)
+  GOOGLE_DCHECK_NE(&from, this);
+  _internal_metadata_.MergeFrom(from._internal_metadata_);
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  (void) cached_has_bits;
+
   fields_.MergeFrom(from.fields_);
 }
 
 void Struct::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Struct)
   if (&from == this) return;
   Clear();
   MergeFrom(from);
 }
 
 void Struct::CopyFrom(const Struct& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Struct)
   if (&from == this) return;
   Clear();
   MergeFrom(from);
 }
 
 bool Struct::IsInitialized() const {
-
   return true;
 }
 
 void Struct::Swap(Struct* other) {
   if (other == this) return;
+  if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+    InternalSwap(other);
+  } else {
+    Struct* temp = New(GetArenaNoVirtual());
+    temp->MergeFrom(*other);
+    other->CopyFrom(*this);
+    InternalSwap(temp);
+    if (GetArenaNoVirtual() == NULL) {
+      delete temp;
+    }
+  }
+}
+void Struct::UnsafeArenaSwap(Struct* other) {
+  if (other == this) return;
+  GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
   InternalSwap(other);
 }
 void Struct::InternalSwap(Struct* other) {
+  using std::swap;
   fields_.Swap(&other->fields_);
   _internal_metadata_.Swap(&other->_internal_metadata_);
-  std::swap(_cached_size_, other->_cached_size_);
 }
 
 ::google::protobuf::Metadata Struct::GetMetadata() const {
-  protobuf_AssignDescriptorsOnce();
-  ::google::protobuf::Metadata metadata;
-  metadata.descriptor = Struct_descriptor_;
-  metadata.reflection = Struct_reflection_;
-  return metadata;
+  protobuf_google_2fprotobuf_2fstruct_2eproto::protobuf_AssignDescriptorsOnce();
+  return ::protobuf_google_2fprotobuf_2fstruct_2eproto::file_level_metadata[kIndexInFileMessages];
 }
 
-#if PROTOBUF_INLINE_NOT_IN_HEADERS
-// Struct
-
-// map<string, .google.protobuf.Value> fields = 1;
-int Struct::fields_size() const {
-  return fields_.size();
-}
-void Struct::clear_fields() {
-  fields_.Clear();
-}
- const ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >&
-Struct::fields() const {
-  // @@protoc_insertion_point(field_map:google.protobuf.Struct.fields)
-  return fields_.GetMap();
-}
- ::google::protobuf::Map< ::std::string, ::google::protobuf::Value >*
-Struct::mutable_fields() {
-  // @@protoc_insertion_point(field_mutable_map:google.protobuf.Struct.fields)
-  return fields_.MutableMap();
-}
-
-#endif  // PROTOBUF_INLINE_NOT_IN_HEADERS
 
 // ===================================================================
 
+void Value::InitAsDefaultInstance() {
+  ::google::protobuf::_Value_default_instance_.null_value_ = 0;
+  ::google::protobuf::_Value_default_instance_.number_value_ = 0;
+  ::google::protobuf::_Value_default_instance_.string_value_.UnsafeSetDefault(
+      &::google::protobuf::internal::GetEmptyStringAlreadyInited());
+  ::google::protobuf::_Value_default_instance_.bool_value_ = false;
+  ::google::protobuf::_Value_default_instance_.struct_value_ = const_cast< ::google::protobuf::Struct*>(
+      ::google::protobuf::Struct::internal_default_instance());
+  ::google::protobuf::_Value_default_instance_.list_value_ = const_cast< ::google::protobuf::ListValue*>(
+      ::google::protobuf::ListValue::internal_default_instance());
+}
+void Value::set_allocated_struct_value(::google::protobuf::Struct* struct_value) {
+  ::google::protobuf::Arena* message_arena = GetArenaNoVirtual();
+  clear_kind();
+  if (struct_value) {
+    ::google::protobuf::Arena* submessage_arena =
+      ::google::protobuf::Arena::GetArena(struct_value);
+    if (message_arena != submessage_arena) {
+      struct_value = ::google::protobuf::internal::GetOwnedMessage(
+          message_arena, struct_value, submessage_arena);
+    }
+    set_has_struct_value();
+    kind_.struct_value_ = struct_value;
+  }
+  // @@protoc_insertion_point(field_set_allocated:google.protobuf.Value.struct_value)
+}
+void Value::set_allocated_list_value(::google::protobuf::ListValue* list_value) {
+  ::google::protobuf::Arena* message_arena = GetArenaNoVirtual();
+  clear_kind();
+  if (list_value) {
+    ::google::protobuf::Arena* submessage_arena =
+      ::google::protobuf::Arena::GetArena(list_value);
+    if (message_arena != submessage_arena) {
+      list_value = ::google::protobuf::internal::GetOwnedMessage(
+          message_arena, list_value, submessage_arena);
+    }
+    set_has_list_value();
+    kind_.list_value_ = list_value;
+  }
+  // @@protoc_insertion_point(field_set_allocated:google.protobuf.Value.list_value)
+}
 #if !defined(_MSC_VER) || _MSC_VER >= 1900
 const int Value::kNullValueFieldNumber;
 const int Value::kNumberValueFieldNumber;
@@ -492,32 +660,57 @@
 
 Value::Value()
   : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+  ::google::protobuf::internal::InitSCC(
+      &protobuf_google_2fprotobuf_2fstruct_2eproto::scc_info_ListValue.base);
   SharedCtor();
   // @@protoc_insertion_point(constructor:google.protobuf.Value)
 }
-
-void Value::InitAsDefaultInstance() {
-  _is_default_instance_ = true;
-  Value_default_oneof_instance_->null_value_ = 0;
-  Value_default_oneof_instance_->number_value_ = 0;
-  Value_default_oneof_instance_->string_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-  Value_default_oneof_instance_->bool_value_ = false;
-  Value_default_oneof_instance_->struct_value_ = const_cast< ::google::protobuf::Struct*>(&::google::protobuf::Struct::default_instance());
-  Value_default_oneof_instance_->list_value_ = const_cast< ::google::protobuf::ListValue*>(&::google::protobuf::ListValue::default_instance());
+Value::Value(::google::protobuf::Arena* arena)
+  : ::google::protobuf::Message(),
+  _internal_metadata_(arena) {
+  ::google::protobuf::internal::InitSCC(&protobuf_google_2fprotobuf_2fstruct_2eproto::scc_info_ListValue.base);
+  SharedCtor();
+  RegisterArenaDtor(arena);
+  // @@protoc_insertion_point(arena_constructor:google.protobuf.Value)
 }
-
 Value::Value(const Value& from)
   : ::google::protobuf::Message(),
-    _internal_metadata_(NULL) {
-  SharedCtor();
-  MergeFrom(from);
+      _internal_metadata_(NULL) {
+  _internal_metadata_.MergeFrom(from._internal_metadata_);
+  clear_has_kind();
+  switch (from.kind_case()) {
+    case kNullValue: {
+      set_null_value(from.null_value());
+      break;
+    }
+    case kNumberValue: {
+      set_number_value(from.number_value());
+      break;
+    }
+    case kStringValue: {
+      set_string_value(from.string_value());
+      break;
+    }
+    case kBoolValue: {
+      set_bool_value(from.bool_value());
+      break;
+    }
+    case kStructValue: {
+      mutable_struct_value()->::google::protobuf::Struct::MergeFrom(from.struct_value());
+      break;
+    }
+    case kListValue: {
+      mutable_list_value()->::google::protobuf::ListValue::MergeFrom(from.list_value());
+      break;
+    }
+    case KIND_NOT_SET: {
+      break;
+    }
+  }
   // @@protoc_insertion_point(copy_constructor:google.protobuf.Value)
 }
 
 void Value::SharedCtor() {
-    _is_default_instance_ = false;
-  ::google::protobuf::internal::GetEmptyString();
-  _cached_size_ = 0;
   clear_has_kind();
 }
 
@@ -527,40 +720,35 @@
 }
 
 void Value::SharedDtor() {
+  GOOGLE_DCHECK(GetArenaNoVirtual() == NULL);
   if (has_kind()) {
     clear_kind();
   }
-  if (this != default_instance_) {
-  }
 }
 
+void Value::ArenaDtor(void* object) {
+  Value* _this = reinterpret_cast< Value* >(object);
+  (void)_this;
+}
+void Value::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
 void Value::SetCachedSize(int size) const {
-  GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
-  _cached_size_ = size;
-  GOOGLE_SAFE_CONCURRENT_WRITES_END();
+  _cached_size_.Set(size);
 }
 const ::google::protobuf::Descriptor* Value::descriptor() {
-  protobuf_AssignDescriptorsOnce();
-  return Value_descriptor_;
+  ::protobuf_google_2fprotobuf_2fstruct_2eproto::protobuf_AssignDescriptorsOnce();
+  return ::protobuf_google_2fprotobuf_2fstruct_2eproto::file_level_metadata[kIndexInFileMessages].descriptor;
 }
 
 const Value& Value::default_instance() {
-  if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
-  return *default_instance_;
+  ::google::protobuf::internal::InitSCC(&protobuf_google_2fprotobuf_2fstruct_2eproto::scc_info_ListValue.base);
+  return *internal_default_instance();
 }
 
-Value* Value::default_instance_ = NULL;
-
-Value* Value::New(::google::protobuf::Arena* arena) const {
-  Value* n = new Value;
-  if (arena != NULL) {
-    arena->Own(n);
-  }
-  return n;
-}
 
 void Value::clear_kind() {
-  switch(kind_case()) {
+// @@protoc_insertion_point(one_of_clear_start:google.protobuf.Value)
+  switch (kind_case()) {
     case kNullValue: {
       // No need to clear
       break;
@@ -570,7 +758,8 @@
       break;
     }
     case kStringValue: {
-      kind_.string_value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
+      kind_.string_value_.Destroy(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
+          GetArenaNoVirtual());
       break;
     }
     case kBoolValue: {
@@ -578,11 +767,15 @@
       break;
     }
     case kStructValue: {
-      delete kind_.struct_value_;
+      if (GetArenaNoVirtual() == NULL) {
+        delete kind_.struct_value_;
+      }
       break;
     }
     case kListValue: {
-      delete kind_.list_value_;
+      if (GetArenaNoVirtual() == NULL) {
+        delete kind_.list_value_;
+      }
       break;
     }
     case KIND_NOT_SET: {
@@ -594,22 +787,29 @@
 
 
 void Value::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.Value)
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  // Prevent compiler warnings about cached_has_bits being unused
+  (void) cached_has_bits;
+
   clear_kind();
+  _internal_metadata_.Clear();
 }
 
 bool Value::MergePartialFromCodedStream(
     ::google::protobuf::io::CodedInputStream* input) {
-#define DO_(EXPRESSION) if (!(EXPRESSION)) goto failure
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
   ::google::protobuf::uint32 tag;
   // @@protoc_insertion_point(parse_start:google.protobuf.Value)
   for (;;) {
-    ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+    ::std::pair<::google::protobuf::uint32, bool> p = input->ReadTagWithCutoffNoLastTag(127u);
     tag = p.first;
     if (!p.second) goto handle_unusual;
     switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
-      // optional .google.protobuf.NullValue null_value = 1;
+      // .google.protobuf.NullValue null_value = 1;
       case 1: {
-        if (tag == 8) {
+        if (static_cast< ::google::protobuf::uint8>(tag) ==
+            static_cast< ::google::protobuf::uint8>(8u /* 8 & 0xFF */)) {
           int value;
           DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
                    int, ::google::protobuf::internal::WireFormatLite::TYPE_ENUM>(
@@ -618,14 +818,13 @@
         } else {
           goto handle_unusual;
         }
-        if (input->ExpectTag(17)) goto parse_number_value;
         break;
       }
 
-      // optional double number_value = 2;
+      // double number_value = 2;
       case 2: {
-        if (tag == 17) {
-         parse_number_value:
+        if (static_cast< ::google::protobuf::uint8>(tag) ==
+            static_cast< ::google::protobuf::uint8>(17u /* 17 & 0xFF */)) {
           clear_kind();
           DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
                    double, ::google::protobuf::internal::WireFormatLite::TYPE_DOUBLE>(
@@ -634,31 +833,29 @@
         } else {
           goto handle_unusual;
         }
-        if (input->ExpectTag(26)) goto parse_string_value;
         break;
       }
 
-      // optional string string_value = 3;
+      // string string_value = 3;
       case 3: {
-        if (tag == 26) {
-         parse_string_value:
+        if (static_cast< ::google::protobuf::uint8>(tag) ==
+            static_cast< ::google::protobuf::uint8>(26u /* 26 & 0xFF */)) {
           DO_(::google::protobuf::internal::WireFormatLite::ReadString(
                 input, this->mutable_string_value()));
           DO_(::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
-            this->string_value().data(), this->string_value().length(),
+            this->string_value().data(), static_cast<int>(this->string_value().length()),
             ::google::protobuf::internal::WireFormatLite::PARSE,
             "google.protobuf.Value.string_value"));
         } else {
           goto handle_unusual;
         }
-        if (input->ExpectTag(32)) goto parse_bool_value;
         break;
       }
 
-      // optional bool bool_value = 4;
+      // bool bool_value = 4;
       case 4: {
-        if (tag == 32) {
-         parse_bool_value:
+        if (static_cast< ::google::protobuf::uint8>(tag) ==
+            static_cast< ::google::protobuf::uint8>(32u /* 32 & 0xFF */)) {
           clear_kind();
           DO_((::google::protobuf::internal::WireFormatLite::ReadPrimitive<
                    bool, ::google::protobuf::internal::WireFormatLite::TYPE_BOOL>(
@@ -667,44 +864,40 @@
         } else {
           goto handle_unusual;
         }
-        if (input->ExpectTag(42)) goto parse_struct_value;
         break;
       }
 
-      // optional .google.protobuf.Struct struct_value = 5;
+      // .google.protobuf.Struct struct_value = 5;
       case 5: {
-        if (tag == 42) {
-         parse_struct_value:
-          DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+        if (static_cast< ::google::protobuf::uint8>(tag) ==
+            static_cast< ::google::protobuf::uint8>(42u /* 42 & 0xFF */)) {
+          DO_(::google::protobuf::internal::WireFormatLite::ReadMessage(
                input, mutable_struct_value()));
         } else {
           goto handle_unusual;
         }
-        if (input->ExpectTag(50)) goto parse_list_value;
         break;
       }
 
-      // optional .google.protobuf.ListValue list_value = 6;
+      // .google.protobuf.ListValue list_value = 6;
       case 6: {
-        if (tag == 50) {
-         parse_list_value:
-          DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtual(
+        if (static_cast< ::google::protobuf::uint8>(tag) ==
+            static_cast< ::google::protobuf::uint8>(50u /* 50 & 0xFF */)) {
+          DO_(::google::protobuf::internal::WireFormatLite::ReadMessage(
                input, mutable_list_value()));
         } else {
           goto handle_unusual;
         }
-        if (input->ExpectAtEnd()) goto success;
         break;
       }
 
       default: {
       handle_unusual:
-        if (tag == 0 ||
-            ::google::protobuf::internal::WireFormatLite::GetTagWireType(tag) ==
-            ::google::protobuf::internal::WireFormatLite::WIRETYPE_END_GROUP) {
+        if (tag == 0) {
           goto success;
         }
-        DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+        DO_(::google::protobuf::internal::WireFormat::SkipField(
+              input, tag, _internal_metadata_.mutable_unknown_fields()));
         break;
       }
     }
@@ -721,65 +914,76 @@
 void Value::SerializeWithCachedSizes(
     ::google::protobuf::io::CodedOutputStream* output) const {
   // @@protoc_insertion_point(serialize_start:google.protobuf.Value)
-  // optional .google.protobuf.NullValue null_value = 1;
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  (void) cached_has_bits;
+
+  // .google.protobuf.NullValue null_value = 1;
   if (has_null_value()) {
     ::google::protobuf::internal::WireFormatLite::WriteEnum(
       1, this->null_value(), output);
   }
 
-  // optional double number_value = 2;
+  // double number_value = 2;
   if (has_number_value()) {
     ::google::protobuf::internal::WireFormatLite::WriteDouble(2, this->number_value(), output);
   }
 
-  // optional string string_value = 3;
+  // string string_value = 3;
   if (has_string_value()) {
     ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
-      this->string_value().data(), this->string_value().length(),
+      this->string_value().data(), static_cast<int>(this->string_value().length()),
       ::google::protobuf::internal::WireFormatLite::SERIALIZE,
       "google.protobuf.Value.string_value");
     ::google::protobuf::internal::WireFormatLite::WriteStringMaybeAliased(
       3, this->string_value(), output);
   }
 
-  // optional bool bool_value = 4;
+  // bool bool_value = 4;
   if (has_bool_value()) {
     ::google::protobuf::internal::WireFormatLite::WriteBool(4, this->bool_value(), output);
   }
 
-  // optional .google.protobuf.Struct struct_value = 5;
+  // .google.protobuf.Struct struct_value = 5;
   if (has_struct_value()) {
     ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
-      5, *kind_.struct_value_, output);
+      5, this->_internal_struct_value(), output);
   }
 
-  // optional .google.protobuf.ListValue list_value = 6;
+  // .google.protobuf.ListValue list_value = 6;
   if (has_list_value()) {
     ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
-      6, *kind_.list_value_, output);
+      6, this->_internal_list_value(), output);
   }
 
+  if ((_internal_metadata_.have_unknown_fields() &&  ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) {
+    ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+        (::google::protobuf::internal::GetProto3PreserveUnknownsDefault()   ? _internal_metadata_.unknown_fields()   : _internal_metadata_.default_instance()), output);
+  }
   // @@protoc_insertion_point(serialize_end:google.protobuf.Value)
 }
 
-::google::protobuf::uint8* Value::SerializeWithCachedSizesToArray(
-    ::google::protobuf::uint8* target) const {
+::google::protobuf::uint8* Value::InternalSerializeWithCachedSizesToArray(
+    bool deterministic, ::google::protobuf::uint8* target) const {
+  (void)deterministic; // Unused
   // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.Value)
-  // optional .google.protobuf.NullValue null_value = 1;
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  (void) cached_has_bits;
+
+  // .google.protobuf.NullValue null_value = 1;
   if (has_null_value()) {
     target = ::google::protobuf::internal::WireFormatLite::WriteEnumToArray(
       1, this->null_value(), target);
   }
 
-  // optional double number_value = 2;
+  // double number_value = 2;
   if (has_number_value()) {
     target = ::google::protobuf::internal::WireFormatLite::WriteDoubleToArray(2, this->number_value(), target);
   }
 
-  // optional string string_value = 3;
+  // string string_value = 3;
   if (has_string_value()) {
     ::google::protobuf::internal::WireFormatLite::VerifyUtf8String(
-      this->string_value().data(), this->string_value().length(),
+      this->string_value().data(), static_cast<int>(this->string_value().length()),
       ::google::protobuf::internal::WireFormatLite::SERIALIZE,
       "google.protobuf.Value.string_value");
     target =
@@ -787,67 +991,77 @@
         3, this->string_value(), target);
   }
 
-  // optional bool bool_value = 4;
+  // bool bool_value = 4;
   if (has_bool_value()) {
     target = ::google::protobuf::internal::WireFormatLite::WriteBoolToArray(4, this->bool_value(), target);
   }
 
-  // optional .google.protobuf.Struct struct_value = 5;
+  // .google.protobuf.Struct struct_value = 5;
   if (has_struct_value()) {
     target = ::google::protobuf::internal::WireFormatLite::
-      WriteMessageNoVirtualToArray(
-        5, *kind_.struct_value_, target);
+      InternalWriteMessageToArray(
+        5, this->_internal_struct_value(), deterministic, target);
   }
 
-  // optional .google.protobuf.ListValue list_value = 6;
+  // .google.protobuf.ListValue list_value = 6;
   if (has_list_value()) {
     target = ::google::protobuf::internal::WireFormatLite::
-      WriteMessageNoVirtualToArray(
-        6, *kind_.list_value_, target);
+      InternalWriteMessageToArray(
+        6, this->_internal_list_value(), deterministic, target);
   }
 
+  if ((_internal_metadata_.have_unknown_fields() &&  ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) {
+    target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+        (::google::protobuf::internal::GetProto3PreserveUnknownsDefault()   ? _internal_metadata_.unknown_fields()   : _internal_metadata_.default_instance()), target);
+  }
   // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.Value)
   return target;
 }
 
-int Value::ByteSize() const {
-  int total_size = 0;
+size_t Value::ByteSizeLong() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.Value)
+  size_t total_size = 0;
 
+  if ((_internal_metadata_.have_unknown_fields() &&  ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) {
+    total_size +=
+      ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+        (::google::protobuf::internal::GetProto3PreserveUnknownsDefault()   ? _internal_metadata_.unknown_fields()   : _internal_metadata_.default_instance()));
+  }
   switch (kind_case()) {
-    // optional .google.protobuf.NullValue null_value = 1;
+    // .google.protobuf.NullValue null_value = 1;
     case kNullValue: {
       total_size += 1 +
         ::google::protobuf::internal::WireFormatLite::EnumSize(this->null_value());
       break;
     }
-    // optional double number_value = 2;
+    // double number_value = 2;
     case kNumberValue: {
       total_size += 1 + 8;
       break;
     }
-    // optional string string_value = 3;
+    // string string_value = 3;
     case kStringValue: {
       total_size += 1 +
         ::google::protobuf::internal::WireFormatLite::StringSize(
           this->string_value());
       break;
     }
-    // optional bool bool_value = 4;
+    // bool bool_value = 4;
     case kBoolValue: {
       total_size += 1 + 1;
       break;
     }
-    // optional .google.protobuf.Struct struct_value = 5;
+    // .google.protobuf.Struct struct_value = 5;
     case kStructValue: {
       total_size += 1 +
-        ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+        ::google::protobuf::internal::WireFormatLite::MessageSize(
           *kind_.struct_value_);
       break;
     }
-    // optional .google.protobuf.ListValue list_value = 6;
+    // .google.protobuf.ListValue list_value = 6;
     case kListValue: {
       total_size += 1 +
-        ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
+        ::google::protobuf::internal::WireFormatLite::MessageSize(
           *kind_.list_value_);
       break;
     }
@@ -855,26 +1069,33 @@
       break;
     }
   }
-  GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
-  _cached_size_ = total_size;
-  GOOGLE_SAFE_CONCURRENT_WRITES_END();
+  int cached_size = ::google::protobuf::internal::ToCachedSize(total_size);
+  SetCachedSize(cached_size);
   return total_size;
 }
 
 void Value::MergeFrom(const ::google::protobuf::Message& from) {
-  if (GOOGLE_PREDICT_FALSE(&from == this)) MergeFromFail(__LINE__);
-  const Value* source = 
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.Value)
+  GOOGLE_DCHECK_NE(&from, this);
+  const Value* source =
       ::google::protobuf::internal::DynamicCastToGenerated<const Value>(
           &from);
   if (source == NULL) {
+  // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.Value)
     ::google::protobuf::internal::ReflectionOps::Merge(from, this);
   } else {
+  // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.Value)
     MergeFrom(*source);
   }
 }
 
 void Value::MergeFrom(const Value& from) {
-  if (GOOGLE_PREDICT_FALSE(&from == this)) MergeFromFail(__LINE__);
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.Value)
+  GOOGLE_DCHECK_NE(&from, this);
+  _internal_metadata_.MergeFrom(from._internal_metadata_);
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  (void) cached_has_bits;
+
   switch (from.kind_case()) {
     case kNullValue: {
       set_null_value(from.null_value());
@@ -907,343 +1128,88 @@
 }
 
 void Value::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.Value)
   if (&from == this) return;
   Clear();
   MergeFrom(from);
 }
 
 void Value::CopyFrom(const Value& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.Value)
   if (&from == this) return;
   Clear();
   MergeFrom(from);
 }
 
 bool Value::IsInitialized() const {
-
   return true;
 }
 
 void Value::Swap(Value* other) {
   if (other == this) return;
+  if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+    InternalSwap(other);
+  } else {
+    Value* temp = New(GetArenaNoVirtual());
+    temp->MergeFrom(*other);
+    other->CopyFrom(*this);
+    InternalSwap(temp);
+    if (GetArenaNoVirtual() == NULL) {
+      delete temp;
+    }
+  }
+}
+void Value::UnsafeArenaSwap(Value* other) {
+  if (other == this) return;
+  GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
   InternalSwap(other);
 }
 void Value::InternalSwap(Value* other) {
-  std::swap(kind_, other->kind_);
-  std::swap(_oneof_case_[0], other->_oneof_case_[0]);
+  using std::swap;
+  swap(kind_, other->kind_);
+  swap(_oneof_case_[0], other->_oneof_case_[0]);
   _internal_metadata_.Swap(&other->_internal_metadata_);
-  std::swap(_cached_size_, other->_cached_size_);
 }
 
 ::google::protobuf::Metadata Value::GetMetadata() const {
-  protobuf_AssignDescriptorsOnce();
-  ::google::protobuf::Metadata metadata;
-  metadata.descriptor = Value_descriptor_;
-  metadata.reflection = Value_reflection_;
-  return metadata;
+  protobuf_google_2fprotobuf_2fstruct_2eproto::protobuf_AssignDescriptorsOnce();
+  return ::protobuf_google_2fprotobuf_2fstruct_2eproto::file_level_metadata[kIndexInFileMessages];
 }
 
-#if PROTOBUF_INLINE_NOT_IN_HEADERS
-// Value
-
-// optional .google.protobuf.NullValue null_value = 1;
-bool Value::has_null_value() const {
-  return kind_case() == kNullValue;
-}
-void Value::set_has_null_value() {
-  _oneof_case_[0] = kNullValue;
-}
-void Value::clear_null_value() {
-  if (has_null_value()) {
-    kind_.null_value_ = 0;
-    clear_has_kind();
-  }
-}
- ::google::protobuf::NullValue Value::null_value() const {
-  // @@protoc_insertion_point(field_get:google.protobuf.Value.null_value)
-  if (has_null_value()) {
-    return static_cast< ::google::protobuf::NullValue >(kind_.null_value_);
-  }
-  return static_cast< ::google::protobuf::NullValue >(0);
-}
- void Value::set_null_value(::google::protobuf::NullValue value) {
-  if (!has_null_value()) {
-    clear_kind();
-    set_has_null_value();
-  }
-  kind_.null_value_ = value;
-  // @@protoc_insertion_point(field_set:google.protobuf.Value.null_value)
-}
-
-// optional double number_value = 2;
-bool Value::has_number_value() const {
-  return kind_case() == kNumberValue;
-}
-void Value::set_has_number_value() {
-  _oneof_case_[0] = kNumberValue;
-}
-void Value::clear_number_value() {
-  if (has_number_value()) {
-    kind_.number_value_ = 0;
-    clear_has_kind();
-  }
-}
- double Value::number_value() const {
-  // @@protoc_insertion_point(field_get:google.protobuf.Value.number_value)
-  if (has_number_value()) {
-    return kind_.number_value_;
-  }
-  return 0;
-}
- void Value::set_number_value(double value) {
-  if (!has_number_value()) {
-    clear_kind();
-    set_has_number_value();
-  }
-  kind_.number_value_ = value;
-  // @@protoc_insertion_point(field_set:google.protobuf.Value.number_value)
-}
-
-// optional string string_value = 3;
-bool Value::has_string_value() const {
-  return kind_case() == kStringValue;
-}
-void Value::set_has_string_value() {
-  _oneof_case_[0] = kStringValue;
-}
-void Value::clear_string_value() {
-  if (has_string_value()) {
-    kind_.string_value_.DestroyNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-    clear_has_kind();
-  }
-}
- const ::std::string& Value::string_value() const {
-  // @@protoc_insertion_point(field_get:google.protobuf.Value.string_value)
-  if (has_string_value()) {
-    return kind_.string_value_.GetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-  }
-  return *&::google::protobuf::internal::GetEmptyStringAlreadyInited();
-}
- void Value::set_string_value(const ::std::string& value) {
-  // @@protoc_insertion_point(field_set:google.protobuf.Value.string_value)
-  if (!has_string_value()) {
-    clear_kind();
-    set_has_string_value();
-    kind_.string_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-  }
-  kind_.string_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), value);
-  // @@protoc_insertion_point(field_set:google.protobuf.Value.string_value)
-}
- void Value::set_string_value(const char* value) {
-  if (!has_string_value()) {
-    clear_kind();
-    set_has_string_value();
-    kind_.string_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-  }
-  kind_.string_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
-      ::std::string(value));
-  // @@protoc_insertion_point(field_set_char:google.protobuf.Value.string_value)
-}
- void Value::set_string_value(const char* value, size_t size) {
-  if (!has_string_value()) {
-    clear_kind();
-    set_has_string_value();
-    kind_.string_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-  }
-  kind_.string_value_.SetNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(), ::std::string(
-      reinterpret_cast<const char*>(value), size));
-  // @@protoc_insertion_point(field_set_pointer:google.protobuf.Value.string_value)
-}
- ::std::string* Value::mutable_string_value() {
-  if (!has_string_value()) {
-    clear_kind();
-    set_has_string_value();
-    kind_.string_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-  }
-  // @@protoc_insertion_point(field_mutable:google.protobuf.Value.string_value)
-  return kind_.string_value_.MutableNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-}
- ::std::string* Value::release_string_value() {
-  if (has_string_value()) {
-    clear_has_kind();
-    return kind_.string_value_.ReleaseNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-  } else {
-    return NULL;
-  }
-}
- void Value::set_allocated_string_value(::std::string* string_value) {
-  if (!has_string_value()) {
-    kind_.string_value_.UnsafeSetDefault(&::google::protobuf::internal::GetEmptyStringAlreadyInited());
-  }
-  clear_kind();
-  if (string_value != NULL) {
-    set_has_string_value();
-    kind_.string_value_.SetAllocatedNoArena(&::google::protobuf::internal::GetEmptyStringAlreadyInited(),
-        string_value);
-  }
-  // @@protoc_insertion_point(field_set_allocated:google.protobuf.Value.string_value)
-}
-
-// optional bool bool_value = 4;
-bool Value::has_bool_value() const {
-  return kind_case() == kBoolValue;
-}
-void Value::set_has_bool_value() {
-  _oneof_case_[0] = kBoolValue;
-}
-void Value::clear_bool_value() {
-  if (has_bool_value()) {
-    kind_.bool_value_ = false;
-    clear_has_kind();
-  }
-}
- bool Value::bool_value() const {
-  // @@protoc_insertion_point(field_get:google.protobuf.Value.bool_value)
-  if (has_bool_value()) {
-    return kind_.bool_value_;
-  }
-  return false;
-}
- void Value::set_bool_value(bool value) {
-  if (!has_bool_value()) {
-    clear_kind();
-    set_has_bool_value();
-  }
-  kind_.bool_value_ = value;
-  // @@protoc_insertion_point(field_set:google.protobuf.Value.bool_value)
-}
-
-// optional .google.protobuf.Struct struct_value = 5;
-bool Value::has_struct_value() const {
-  return kind_case() == kStructValue;
-}
-void Value::set_has_struct_value() {
-  _oneof_case_[0] = kStructValue;
-}
-void Value::clear_struct_value() {
-  if (has_struct_value()) {
-    delete kind_.struct_value_;
-    clear_has_kind();
-  }
-}
- const ::google::protobuf::Struct& Value::struct_value() const {
-  // @@protoc_insertion_point(field_get:google.protobuf.Value.struct_value)
-  return has_struct_value()
-      ? *kind_.struct_value_
-      : ::google::protobuf::Struct::default_instance();
-}
-::google::protobuf::Struct* Value::mutable_struct_value() {
-  if (!has_struct_value()) {
-    clear_kind();
-    set_has_struct_value();
-    kind_.struct_value_ = new ::google::protobuf::Struct;
-  }
-  // @@protoc_insertion_point(field_mutable:google.protobuf.Value.struct_value)
-  return kind_.struct_value_;
-}
-::google::protobuf::Struct* Value::release_struct_value() {
-  if (has_struct_value()) {
-    clear_has_kind();
-    ::google::protobuf::Struct* temp = kind_.struct_value_;
-    kind_.struct_value_ = NULL;
-    return temp;
-  } else {
-    return NULL;
-  }
-}
-void Value::set_allocated_struct_value(::google::protobuf::Struct* struct_value) {
-  clear_kind();
-  if (struct_value) {
-    set_has_struct_value();
-    kind_.struct_value_ = struct_value;
-  }
-  // @@protoc_insertion_point(field_set_allocated:google.protobuf.Value.struct_value)
-}
-
-// optional .google.protobuf.ListValue list_value = 6;
-bool Value::has_list_value() const {
-  return kind_case() == kListValue;
-}
-void Value::set_has_list_value() {
-  _oneof_case_[0] = kListValue;
-}
-void Value::clear_list_value() {
-  if (has_list_value()) {
-    delete kind_.list_value_;
-    clear_has_kind();
-  }
-}
- const ::google::protobuf::ListValue& Value::list_value() const {
-  // @@protoc_insertion_point(field_get:google.protobuf.Value.list_value)
-  return has_list_value()
-      ? *kind_.list_value_
-      : ::google::protobuf::ListValue::default_instance();
-}
-::google::protobuf::ListValue* Value::mutable_list_value() {
-  if (!has_list_value()) {
-    clear_kind();
-    set_has_list_value();
-    kind_.list_value_ = new ::google::protobuf::ListValue;
-  }
-  // @@protoc_insertion_point(field_mutable:google.protobuf.Value.list_value)
-  return kind_.list_value_;
-}
-::google::protobuf::ListValue* Value::release_list_value() {
-  if (has_list_value()) {
-    clear_has_kind();
-    ::google::protobuf::ListValue* temp = kind_.list_value_;
-    kind_.list_value_ = NULL;
-    return temp;
-  } else {
-    return NULL;
-  }
-}
-void Value::set_allocated_list_value(::google::protobuf::ListValue* list_value) {
-  clear_kind();
-  if (list_value) {
-    set_has_list_value();
-    kind_.list_value_ = list_value;
-  }
-  // @@protoc_insertion_point(field_set_allocated:google.protobuf.Value.list_value)
-}
-
-bool Value::has_kind() const {
-  return kind_case() != KIND_NOT_SET;
-}
-void Value::clear_has_kind() {
-  _oneof_case_[0] = KIND_NOT_SET;
-}
-Value::KindCase Value::kind_case() const {
-  return Value::KindCase(_oneof_case_[0]);
-}
-#endif  // PROTOBUF_INLINE_NOT_IN_HEADERS
 
 // ===================================================================
 
+void ListValue::InitAsDefaultInstance() {
+}
 #if !defined(_MSC_VER) || _MSC_VER >= 1900
 const int ListValue::kValuesFieldNumber;
 #endif  // !defined(_MSC_VER) || _MSC_VER >= 1900
 
 ListValue::ListValue()
   : ::google::protobuf::Message(), _internal_metadata_(NULL) {
+  ::google::protobuf::internal::InitSCC(
+      &protobuf_google_2fprotobuf_2fstruct_2eproto::scc_info_ListValue.base);
   SharedCtor();
   // @@protoc_insertion_point(constructor:google.protobuf.ListValue)
 }
-
-void ListValue::InitAsDefaultInstance() {
-  _is_default_instance_ = true;
+ListValue::ListValue(::google::protobuf::Arena* arena)
+  : ::google::protobuf::Message(),
+  _internal_metadata_(arena),
+  values_(arena) {
+  ::google::protobuf::internal::InitSCC(&protobuf_google_2fprotobuf_2fstruct_2eproto::scc_info_ListValue.base);
+  SharedCtor();
+  RegisterArenaDtor(arena);
+  // @@protoc_insertion_point(arena_constructor:google.protobuf.ListValue)
 }
-
 ListValue::ListValue(const ListValue& from)
   : ::google::protobuf::Message(),
-    _internal_metadata_(NULL) {
-  SharedCtor();
-  MergeFrom(from);
+      _internal_metadata_(NULL),
+      values_(from.values_) {
+  _internal_metadata_.MergeFrom(from._internal_metadata_);
   // @@protoc_insertion_point(copy_constructor:google.protobuf.ListValue)
 }
 
 void ListValue::SharedCtor() {
-    _is_default_instance_ = false;
-  _cached_size_ = 0;
 }
 
 ListValue::~ListValue() {
@@ -1252,73 +1218,68 @@
 }
 
 void ListValue::SharedDtor() {
-  if (this != default_instance_) {
-  }
+  GOOGLE_DCHECK(GetArenaNoVirtual() == NULL);
 }
 
+void ListValue::ArenaDtor(void* object) {
+  ListValue* _this = reinterpret_cast< ListValue* >(object);
+  (void)_this;
+}
+void ListValue::RegisterArenaDtor(::google::protobuf::Arena* arena) {
+}
 void ListValue::SetCachedSize(int size) const {
-  GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
-  _cached_size_ = size;
-  GOOGLE_SAFE_CONCURRENT_WRITES_END();
+  _cached_size_.Set(size);
 }
 const ::google::protobuf::Descriptor* ListValue::descriptor() {
-  protobuf_AssignDescriptorsOnce();
-  return ListValue_descriptor_;
+  ::protobuf_google_2fprotobuf_2fstruct_2eproto::protobuf_AssignDescriptorsOnce();
+  return ::protobuf_google_2fprotobuf_2fstruct_2eproto::file_level_metadata[kIndexInFileMessages].descriptor;
 }
 
 const ListValue& ListValue::default_instance() {
-  if (default_instance_ == NULL) protobuf_AddDesc_google_2fprotobuf_2fstruct_2eproto();
-  return *default_instance_;
+  ::google::protobuf::internal::InitSCC(&protobuf_google_2fprotobuf_2fstruct_2eproto::scc_info_ListValue.base);
+  return *internal_default_instance();
 }
 
-ListValue* ListValue::default_instance_ = NULL;
-
-ListValue* ListValue::New(::google::protobuf::Arena* arena) const {
-  ListValue* n = new ListValue;
-  if (arena != NULL) {
-    arena->Own(n);
-  }
-  return n;
-}
 
 void ListValue::Clear() {
+// @@protoc_insertion_point(message_clear_start:google.protobuf.ListValue)
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  // Prevent compiler warnings about cached_has_bits being unused
+  (void) cached_has_bits;
+
   values_.Clear();
+  _internal_metadata_.Clear();
 }
 
 bool ListValue::MergePartialFromCodedStream(
     ::google::protobuf::io::CodedInputStream* input) {
-#define DO_(EXPRESSION) if (!(EXPRESSION)) goto failure
+#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure
   ::google::protobuf::uint32 tag;
   // @@protoc_insertion_point(parse_start:google.protobuf.ListValue)
   for (;;) {
-    ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoff(127);
+    ::std::pair<::google::protobuf::uint32, bool> p = input->ReadTagWithCutoffNoLastTag(127u);
     tag = p.first;
     if (!p.second) goto handle_unusual;
     switch (::google::protobuf::internal::WireFormatLite::GetTagFieldNumber(tag)) {
       // repeated .google.protobuf.Value values = 1;
       case 1: {
-        if (tag == 10) {
-          DO_(input->IncrementRecursionDepth());
-         parse_loop_values:
-          DO_(::google::protobuf::internal::WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
+        if (static_cast< ::google::protobuf::uint8>(tag) ==
+            static_cast< ::google::protobuf::uint8>(10u /* 10 & 0xFF */)) {
+          DO_(::google::protobuf::internal::WireFormatLite::ReadMessage(
                 input, add_values()));
         } else {
           goto handle_unusual;
         }
-        if (input->ExpectTag(10)) goto parse_loop_values;
-        input->UnsafeDecrementRecursionDepth();
-        if (input->ExpectAtEnd()) goto success;
         break;
       }
 
       default: {
       handle_unusual:
-        if (tag == 0 ||
-            ::google::protobuf::internal::WireFormatLite::GetTagWireType(tag) ==
-            ::google::protobuf::internal::WireFormatLite::WIRETYPE_END_GROUP) {
+        if (tag == 0) {
           goto success;
         }
-        DO_(::google::protobuf::internal::WireFormatLite::SkipField(input, tag));
+        DO_(::google::protobuf::internal::WireFormat::SkipField(
+              input, tag, _internal_metadata_.mutable_unknown_fields()));
         break;
       }
     }
@@ -1335,135 +1296,164 @@
 void ListValue::SerializeWithCachedSizes(
     ::google::protobuf::io::CodedOutputStream* output) const {
   // @@protoc_insertion_point(serialize_start:google.protobuf.ListValue)
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  (void) cached_has_bits;
+
   // repeated .google.protobuf.Value values = 1;
-  for (unsigned int i = 0, n = this->values_size(); i < n; i++) {
+  for (unsigned int i = 0,
+      n = static_cast<unsigned int>(this->values_size()); i < n; i++) {
     ::google::protobuf::internal::WireFormatLite::WriteMessageMaybeToArray(
-      1, this->values(i), output);
+      1,
+      this->values(static_cast<int>(i)),
+      output);
   }
 
+  if ((_internal_metadata_.have_unknown_fields() &&  ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) {
+    ::google::protobuf::internal::WireFormat::SerializeUnknownFields(
+        (::google::protobuf::internal::GetProto3PreserveUnknownsDefault()   ? _internal_metadata_.unknown_fields()   : _internal_metadata_.default_instance()), output);
+  }
   // @@protoc_insertion_point(serialize_end:google.protobuf.ListValue)
 }
 
-::google::protobuf::uint8* ListValue::SerializeWithCachedSizesToArray(
-    ::google::protobuf::uint8* target) const {
+::google::protobuf::uint8* ListValue::InternalSerializeWithCachedSizesToArray(
+    bool deterministic, ::google::protobuf::uint8* target) const {
+  (void)deterministic; // Unused
   // @@protoc_insertion_point(serialize_to_array_start:google.protobuf.ListValue)
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  (void) cached_has_bits;
+
   // repeated .google.protobuf.Value values = 1;
-  for (unsigned int i = 0, n = this->values_size(); i < n; i++) {
+  for (unsigned int i = 0,
+      n = static_cast<unsigned int>(this->values_size()); i < n; i++) {
     target = ::google::protobuf::internal::WireFormatLite::
-      WriteMessageNoVirtualToArray(
-        1, this->values(i), target);
+      InternalWriteMessageToArray(
+        1, this->values(static_cast<int>(i)), deterministic, target);
   }
 
+  if ((_internal_metadata_.have_unknown_fields() &&  ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) {
+    target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray(
+        (::google::protobuf::internal::GetProto3PreserveUnknownsDefault()   ? _internal_metadata_.unknown_fields()   : _internal_metadata_.default_instance()), target);
+  }
   // @@protoc_insertion_point(serialize_to_array_end:google.protobuf.ListValue)
   return target;
 }
 
-int ListValue::ByteSize() const {
-  int total_size = 0;
+size_t ListValue::ByteSizeLong() const {
+// @@protoc_insertion_point(message_byte_size_start:google.protobuf.ListValue)
+  size_t total_size = 0;
 
-  // repeated .google.protobuf.Value values = 1;
-  total_size += 1 * this->values_size();
-  for (int i = 0; i < this->values_size(); i++) {
+  if ((_internal_metadata_.have_unknown_fields() &&  ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) {
     total_size +=
-      ::google::protobuf::internal::WireFormatLite::MessageSizeNoVirtual(
-        this->values(i));
+      ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize(
+        (::google::protobuf::internal::GetProto3PreserveUnknownsDefault()   ? _internal_metadata_.unknown_fields()   : _internal_metadata_.default_instance()));
+  }
+  // repeated .google.protobuf.Value values = 1;
+  {
+    unsigned int count = static_cast<unsigned int>(this->values_size());
+    total_size += 1UL * count;
+    for (unsigned int i = 0; i < count; i++) {
+      total_size +=
+        ::google::protobuf::internal::WireFormatLite::MessageSize(
+          this->values(static_cast<int>(i)));
+    }
   }
 
-  GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN();
-  _cached_size_ = total_size;
-  GOOGLE_SAFE_CONCURRENT_WRITES_END();
+  int cached_size = ::google::protobuf::internal::ToCachedSize(total_size);
+  SetCachedSize(cached_size);
   return total_size;
 }
 
 void ListValue::MergeFrom(const ::google::protobuf::Message& from) {
-  if (GOOGLE_PREDICT_FALSE(&from == this)) MergeFromFail(__LINE__);
-  const ListValue* source = 
+// @@protoc_insertion_point(generalized_merge_from_start:google.protobuf.ListValue)
+  GOOGLE_DCHECK_NE(&from, this);
+  const ListValue* source =
       ::google::protobuf::internal::DynamicCastToGenerated<const ListValue>(
           &from);
   if (source == NULL) {
+  // @@protoc_insertion_point(generalized_merge_from_cast_fail:google.protobuf.ListValue)
     ::google::protobuf::internal::ReflectionOps::Merge(from, this);
   } else {
+  // @@protoc_insertion_point(generalized_merge_from_cast_success:google.protobuf.ListValue)
     MergeFrom(*source);
   }
 }
 
 void ListValue::MergeFrom(const ListValue& from) {
-  if (GOOGLE_PREDICT_FALSE(&from == this)) MergeFromFail(__LINE__);
+// @@protoc_insertion_point(class_specific_merge_from_start:google.protobuf.ListValue)
+  GOOGLE_DCHECK_NE(&from, this);
+  _internal_metadata_.MergeFrom(from._internal_metadata_);
+  ::google::protobuf::uint32 cached_has_bits = 0;
+  (void) cached_has_bits;
+
   values_.MergeFrom(from.values_);
 }
 
 void ListValue::CopyFrom(const ::google::protobuf::Message& from) {
+// @@protoc_insertion_point(generalized_copy_from_start:google.protobuf.ListValue)
   if (&from == this) return;
   Clear();
   MergeFrom(from);
 }
 
 void ListValue::CopyFrom(const ListValue& from) {
+// @@protoc_insertion_point(class_specific_copy_from_start:google.protobuf.ListValue)
   if (&from == this) return;
   Clear();
   MergeFrom(from);
 }
 
 bool ListValue::IsInitialized() const {
-
   return true;
 }
 
 void ListValue::Swap(ListValue* other) {
   if (other == this) return;
+  if (GetArenaNoVirtual() == other->GetArenaNoVirtual()) {
+    InternalSwap(other);
+  } else {
+    ListValue* temp = New(GetArenaNoVirtual());
+    temp->MergeFrom(*other);
+    other->CopyFrom(*this);
+    InternalSwap(temp);
+    if (GetArenaNoVirtual() == NULL) {
+      delete temp;
+    }
+  }
+}
+void ListValue::UnsafeArenaSwap(ListValue* other) {
+  if (other == this) return;
+  GOOGLE_DCHECK(GetArenaNoVirtual() == other->GetArenaNoVirtual());
   InternalSwap(other);
 }
 void ListValue::InternalSwap(ListValue* other) {
-  values_.UnsafeArenaSwap(&other->values_);
+  using std::swap;
+  CastToBase(&values_)->InternalSwap(CastToBase(&other->values_));
   _internal_metadata_.Swap(&other->_internal_metadata_);
-  std::swap(_cached_size_, other->_cached_size_);
 }
 
 ::google::protobuf::Metadata ListValue::GetMetadata() const {
-  protobuf_AssignDescriptorsOnce();
-  ::google::protobuf::Metadata metadata;
-  metadata.descriptor = ListValue_descriptor_;
-  metadata.reflection = ListValue_reflection_;
-  return metadata;
+  protobuf_google_2fprotobuf_2fstruct_2eproto::protobuf_AssignDescriptorsOnce();
+  return ::protobuf_google_2fprotobuf_2fstruct_2eproto::file_level_metadata[kIndexInFileMessages];
 }
 
-#if PROTOBUF_INLINE_NOT_IN_HEADERS
-// ListValue
-
-// repeated .google.protobuf.Value values = 1;
-int ListValue::values_size() const {
-  return values_.size();
-}
-void ListValue::clear_values() {
-  values_.Clear();
-}
-const ::google::protobuf::Value& ListValue::values(int index) const {
-  // @@protoc_insertion_point(field_get:google.protobuf.ListValue.values)
-  return values_.Get(index);
-}
-::google::protobuf::Value* ListValue::mutable_values(int index) {
-  // @@protoc_insertion_point(field_mutable:google.protobuf.ListValue.values)
-  return values_.Mutable(index);
-}
-::google::protobuf::Value* ListValue::add_values() {
-  // @@protoc_insertion_point(field_add:google.protobuf.ListValue.values)
-  return values_.Add();
-}
-::google::protobuf::RepeatedPtrField< ::google::protobuf::Value >*
-ListValue::mutable_values() {
-  // @@protoc_insertion_point(field_mutable_list:google.protobuf.ListValue.values)
-  return &values_;
-}
-const ::google::protobuf::RepeatedPtrField< ::google::protobuf::Value >&
-ListValue::values() const {
-  // @@protoc_insertion_point(field_list:google.protobuf.ListValue.values)
-  return values_;
-}
-
-#endif  // PROTOBUF_INLINE_NOT_IN_HEADERS
 
 // @@protoc_insertion_point(namespace_scope)
-
+}  // namespace protobuf
+}  // namespace google
+namespace google {
+namespace protobuf {
+template<> GOOGLE_PROTOBUF_ATTRIBUTE_NOINLINE ::google::protobuf::Struct_FieldsEntry_DoNotUse* Arena::CreateMaybeMessage< ::google::protobuf::Struct_FieldsEntry_DoNotUse >(Arena* arena) {
+  return Arena::CreateMessageInternal< ::google::protobuf::Struct_FieldsEntry_DoNotUse >(arena);
+}
+template<> GOOGLE_PROTOBUF_ATTRIBUTE_NOINLINE ::google::protobuf::Struct* Arena::CreateMaybeMessage< ::google::protobuf::Struct >(Arena* arena) {
+  return Arena::CreateMessageInternal< ::google::protobuf::Struct >(arena);
+}
+template<> GOOGLE_PROTOBUF_ATTRIBUTE_NOINLINE ::google::protobuf::Value* Arena::CreateMaybeMessage< ::google::protobuf::Value >(Arena* arena) {
+  return Arena::CreateMessageInternal< ::google::protobuf::Value >(arena);
+}
+template<> GOOGLE_PROTOBUF_ATTRIBUTE_NOINLINE ::google::protobuf::ListValue* Arena::CreateMaybeMessage< ::google::protobuf::ListValue >(Arena* arena) {
+  return Arena::CreateMessageInternal< ::google::protobuf::ListValue >(arena);
+}
 }  // namespace protobuf
 }  // namespace google
 
